Skip to content

WebSocket receive path copies every frame before deserialization #32

Description

@nficano

WebSocketTransport.ReceiveAsync rents a buffer, writes each received frame into a new MemoryStream, then calls ms.ToArray() before deserializing. For the common case where a complete envelope fits in one receive buffer, this allocates both the MemoryStream backing storage and a second array copy for every message. ARCP transports can carry high-volume event streams, so this avoidable allocation path can become noticeable under load.

The relevant locations are src/Arcp.Core/Transport/WebSocketTransport.cs:48, src/Arcp.Core/Transport/WebSocketTransport.cs:53, src/Arcp.Core/Transport/WebSocketTransport.cs:63, and src/Arcp.Core/Transport/WebSocketTransport.cs:72.

Fix prompt: Optimize WebSocketTransport.ReceiveAsync to deserialize directly from the rented buffer when EndOfMessage is true on the first receive, and use a pooled growable buffer such as ArrayBufferWriter<byte> or a reusable pooled stream for fragmented messages. Preserve the existing behavior for close frames and malformed JSON, return rented arrays in all paths, and add allocation-sensitive tests or benchmarks that cover single-frame and fragmented messages.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    performancePerformance and allocation improvementsseverity:lowLow severity

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions