Inconsistent typing for WebSocketMessage and WebSocketClient.run() callback in v2.8.0
Chưa có ai nhận issue này.
Đánh giá
- Độ khó
- 3/5
- Thời gian dự kiến
- 1-2 ngày
- Mức phù hợp với người mới
- 55/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
- api, networking
Hướng nghiên cứu
Bắt đầu với các định nghĩa của WebSocketMessage, WebSocketClient.run(), parse_single() và parse() được đề cập trong issue, sau đó kiểm tra các giá trị trong thời gian chạy và chữ ký kiểu của chúng. Xác nhận xem WebSocketMessage biểu diễn một sự kiện đã được phân tích duy nhất hay một batch, điều chỉnh các annotation của callback và parser cho phù hợp, đồng thời đưa vào các annotation được đề xuất cho run() để Pyright/Pylance chấp nhận một handler được định kiểu chính xác.
Do mô hình lập chỉ mục viết ra từ nội dung của issue.
Mô tả
Hi Massive team,
I noticed an inconsistency in the websocket typing in Massive Python SDK v2.8.0.
WebSocketMessage is currently defined as a NewType over a list of parsed event models:
WebSocketMessage = NewType(
"WebSocketMessage",
List[
Union[
EquityAgg,
CurrencyAgg,
EquityTrade,
...
]
],
)
However, WebSocketClient.run() is typed as accepting a callback of:
Callable[[List[WebSocketMessage]], None]
This effectively makes the callback parameter type a nested list-like structure:
List[WebSocketMessage], while WebSocketMessage itself already represents a list
of parsed websocket events.
This causes type checkers such as Pyright/Pylance to reject handlers like this:
def handle_msg(messages: WebSocketMessage) -> None:
for message in messages:
if isinstance(message, EquityAgg):
...
with an error similar to:
Argument of type "(messages: WebSocketMessage) -> None" cannot be assigned to parameter "handle_msg"
Type "(messages: WebSocketMessage) -> None" is not assignable to type "(List[WebSocketMessage]) -> None"
There also seems to be a related inconsistency in the parser:
def parse_single(...) -> Optional[WebSocketMessage]:
parsed = model_class.from_dict(data)
return cast(WebSocketMessage, parsed)
At runtime, parsed is a single event object such as EquityAgg, not a list. Then
parse() returns List[WebSocketMessage].
So there appear to be two possible fixes:
- If
WebSocketMessageis intended to mean a single parsed event, redefine it as
a union of event model types, not a list. - If
WebSocketMessageis intended to mean a batch of parsed events, thenrun()
should acceptCallable[[WebSocketMessage], None], andparse_single()should
not cast individual event objects toWebSocketMessage.
Based on the current runtime behavior, option 1 seems more natural:
WebSocketMessage = NewType(
"WebSocketMessage",
Union[
EquityAgg,
CurrencyAgg,
EquityTrade,
...
],
)
or alternatively, using a type alias instead of NewType:
WebSocketMessage = Union[
EquityAgg,
CurrencyAgg,
EquityTrade,
...
]
Then these signatures would make sense:
def parse_single(...) -> Optional[WebSocketMessage]: ...
def parse(...) -> List[WebSocketMessage]: ...
def run(
self,
handle_msg: Callable[[List[WebSocketMessage]], None] | Callable[[str | bytes], None],
close_timeout: int = 1,
**kwargs: Any,
) -> None: ...
One smaller typing improvement: run() currently leaves **kwargs unknown for
Pyright/Pylance. Annotating it as **kwargs: Any and adding -> None would avoid
"partially unknown" warnings.
Thanks.
- Ngôn ngữ chính
- Python
- Star
- 1.5k
- Fork
- 362
- 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
Chưa lập chỉ mục được hướng dẫn đóng góp cho kho mã nguồn này
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 massive-com/client-python
-
bug
Độ khó 1/5 Dưới một giờ Mức phù hợp với người mới 72/100
massive-com/client-python#876 · 1 bình luận ·
-
enhancement
Độ khó 3/5 1-2 ngày Mức phù hợp với người mới 72/100
massive-com/client-python#1031 ·
-
enhancement
Độ khó 4/5 3-5 ngày Mức phù hợp với người mới 45/100
massive-com/client-python#1029 ·
-
Độ khó 4/5 3-5 ngày Mức phù hợp với người mới 35/100
massive-com/client-python#1028 ·
-
bug
Độ khó 4/5 3-5 ngày Mức phù hợp với người mới 50/100
massive-com/client-python#1016 ·
Tất cả issue của massive-com/client-python
Issue tương tự
-
documentation help wanted
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 90/100
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 90/100
simonw/sqlite-utils#872 ·
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 88/100
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 82/100
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 78/100