feat(data-connect): add binary websocket message conversion#9805
feat(data-connect): add binary websocket message conversion#9805stephenarosaj merged 3 commits intopasta/mainfrom
Conversation
|
There was a problem hiding this comment.
Code Review
This pull request introduces a new transport layer for Firebase Data Connect, including a DataConnectTransportManager to route requests between a REST-based transport and a new WebSocket-based streaming transport. The changes include the implementation of AbstractDataConnectStreamTransport and WebSocketTransport to handle subscriptions. My review identified several areas for improvement: the error handling for unrecognized request IDs in the stream transport is too aggressive and should be softened to avoid unnecessary connection closures; the decodeBinaryResponse method in WebSocketTransport should be optimized and typed more strictly; the binaryType configuration for WebSockets should be unified to ensure consistent binary data handling; and the isUnableToConnect property currently disables critical fallback logic that needs to be addressed for production resilience.
I am having trouble creating individual review comments. Click here to see my feedback.
packages/data-connect/src/network/stream/streamTransport.ts (581-586)
Throwing an error for an unrecognized requestId is too aggressive. In a streaming environment, it is common to receive "late" messages for requests that have already been cancelled or cleaned up on the client side (e.g., after an unsubscribe call). Throwing here will trigger a protocol error that closes the entire WebSocket connection, affecting all other active subscriptions. It is safer to simply ignore these messages.
}packages/data-connect/src/network/stream/websocket.ts (322-325)
The decodeBinaryResponse method should have more precise types. The input data can be an ArrayBuffer (when binaryType is set to 'arraybuffer') or a typed array, and the return type should be string rather than any. Additionally, creating a new TextDecoder instance for every message is slightly inefficient; consider making it a class member.
private decodeBinaryResponse(data: ArrayBuffer | ArrayBufferView): string {
const decoder = new TextDecoder('utf-8');
return decoder.decode(data);
}
packages/data-connect/src/network/stream/websocket.ts (144-147)
It is safer to always set binaryType to 'arraybuffer' regardless of whether the emulator is being used. If the emulator ever sends binary data in a browser environment, the default binaryType is 'blob', which TextDecoder cannot handle directly, leading to a runtime error in decodeBinaryResponse. Setting it to 'arraybuffer' ensures consistent behavior for all binary messages without affecting string-based messages.
// prod sends as binary, emulator sends as JSON strings.
// Setting binaryType to 'arraybuffer' ensures binary messages are handled consistently.
this.connection!.binaryType = 'arraybuffer';packages/data-connect/src/network/stream/streamTransport.ts (74-76)
Hardcoding isUnableToConnect to false effectively disables the fallback and error handling logic in DataConnectTransportManager. The manager relies on this property to decide whether to retry a failed streaming request via the REST transport. While the TODO notes this will be implemented later, the current state prevents the resilience features of the transport layer from functioning.
Update WebSocket message handling to handle binary messages, converting them to strings before parsing.