Using async changes thread for non-async callbacks which is unexpected
Chưa có ai nhận issue này.
Đánh giá
- Độ khó
- 4/5
- Thời gian dự kiến
- 3-5 ngày
- Mức phù hợp với người mới
- 52/100
- Loại issue
- Lỗi
- Độ rõ ràng
- Khá rõ ràng
- Mức độ hoạt động
- Ít trao đổi
- Công nghệ
- python
- Lĩnh vực
- networking
Hướng nghiên cứu
Bắt đầu với can/notifier.py tại các dòng _rx_thread() được tham chiếu và lần theo _on_message_received() cùng với luồng lập lịch của asyncio. Xem xét các issue #1938 và #1912 cùng với thay đổi này. Được coi là hoàn tất khi các callback không async có thể vẫn chạy trên thread nhận CAN khi được cấu hình như vậy, trong khi các callback async được lập lịch an toàn từ một trong hai thread mà không thay đổi hành vi mặc định.
Do mô hình lập chỉ mục viết ra từ nội dung của issue.
Mô tả
Using the can library with async enabled Notifier change the thread which all callbacks is called from. Without async, the notifier callbacks are run in the thread of the can rx thread. With async, it runs the callbacks via loop.call_soon_threadsafe() which cause the notifier callbacks to be run in the main async thread instead. This changes behavior for all callbacks, not just async callbacks, which is unexpected. E.g. if using a non-async can protocol stack plus another async protocol stack together might create problems due to the change of callback threads.
I propose a fix that prevents the async call_soon_threadsafe in Notifier._rx_thread() with the introduction of a setting run_message_reception_in_eventloop. Then the user can chose to opt out of running the regular non-async callbacks in the asyncio main thread. The default should be True so we don't change the current behavior.
def _rx_thread(self, bus: BusABC) -> None:
# determine message handling callable early, not inside while loop
if self._loop and self.run_message_reception_in_eventloop: # <--- NEW
handle_message: Callable[[Message], Any] = functools.partial(
self._loop.call_soon_threadsafe,
self._on_message_received, # type: ignore[arg-type]
)
else:
handle_message = self._on_message_received
A change is required in Notifier._on_message_received(). This function might be called in either threads, so calling the asyncio coroutine must be made thread safe:
def _on_message_received(self, msg: Message) -> None:
for callback in self.listeners:
res = callback(msg)
if res and self._loop and asyncio.iscoroutine(res):
# Schedule coroutine
# In __init__: self._tasks: set[asyncio.Task] = set()
task = asyncio.run_coroutine_threadsafe(res, self._loop)
When looking at this, #1938 and #1912 should be addressed in the same round.
- Ngôn ngữ chính
- Python
- Star
- 1.6k
- Fork
- 697
- Chỉ số merge pull request
- Không có pull request nào được merge trong 30 ngày
Hướng dẫn đóng góp
Bắt đầu từ đâu
- Đọc hết issue, rồi đọc hướng dẫn đóng góp của dự án.
- Bình luận trên issue rằng bạn sẽ nhận — tránh hai người làm cùng một việc.
- Fork repository và làm thay đổi trên một nhánh.
- Mở pull request có tham chiếu số hiệu của issue.
Issue khác của hardbyte/python-can
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 88/100
hardbyte/python-can#2103 ·
-
bug
Độ khó 1/5 Dưới một giờ Mức phù hợp với người mới 78/100
hardbyte/python-can#2077 · 1 bình luận · 1 reaction ·
-
bug
Độ khó 1/5 Dưới một giờ Mức phù hợp với người mới 68/100
hardbyte/python-can#1922 · 1 reaction ·
-
enhancement
Độ khó 5/5 Hơn một tuần Mức phù hợp với người mới 30/100
hardbyte/python-can#2102 ·
-
bug
Độ khó 3/5 1-2 ngày Mức phù hợp với người mới 68/100
hardbyte/python-can#2092 ·
Tất cả issue của hardbyte/python-can
Issue tương tự
-
bug
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 75/100
stephrobert/dsoxlab#238 ·
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 75/100
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 75/100
sublimehq/package_control#1780 ·
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 65/100
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 70/100
nwg-piotr/nwg-displays#145 ·