vanguard-go icon indicating copy to clipboard operation
vanguard-go copied to clipboard

Feature Request: Server streams for general REST APIs

Open devnev opened this issue 9 months ago • 4 comments

I've tried using vanguard-go as it seemed appealing to get all of REST, connect and grpc in one go. However, when I got to a streaming API the REST variant gave an error indicating that it is unsupported. It looks like from the implementation that only HttpBody responses can be streamed. So in the end I've gone back to connectrpc+(grpcgateway+grpchan) which has reminded me while vanguard-go seemed so appealing in the first place 😁 ...

Are there any plans for supporting arbitrary response stream types?

I understand there's a bunch of concerns, in particular how to send the final status - e.g. trailers are still very, very far from being supported by browsers to a degree that would make them suitable for the response status. Content-type negotation might be a passable way to get around these, i.e. the client has to opt in to a certain way of streaming responses by having a particular protocol version in its accept header.

devnev avatar Feb 25 '25 11:02 devnev

Hi devnev, theres not currently a well defined spec for how streaming RPCs map to REST style requests. There is support for file streaming with the use of google.api.HttpBody. Streaming implementation usually want to use something like websockets or the new WebTransport (HTTP3) but this is very project specific. So to support streaming I think we'd want to provide pluggable protocols to allow users to change the client encoder to fit their use case. However, there is no planned support for this.

emcfarlane avatar Feb 28 '25 14:02 emcfarlane

How does gRPC Gateway handle it? I would expect this be a highly sought after feature. The lack of this feature is the only reason I'm still using gRPC Gateway tbh.

nu11ptr avatar Apr 12 '25 00:04 nu11ptr

gRPC Gateway has a custom format for server-to-client streams, it's ndjson/jsonlines where the response messages are wrapped in {"result":<msg>}, and a non-OK status produces a final {"error":<status msg>} line. Oddly, the content-type is still set to application/json rather than something more appropriate like application/x-ndjson or application/x-jsonlines.

The event-stream format has recently gained popularity with the advent of AI chats, as that is the response stream format used by OpenAI and the like. That might present a slightly more standardised alternative.

devnev avatar Apr 12 '25 01:04 devnev

I opened a PR to support the SSE as an option on the REST protocol.

There were some open questions in my mind as I implemented around event types and event ids for reconnect. Ended up implementing these as directives that can be passed through the http annotations, although I admit this is a little heavy handed and not necessarily compatible with any other service which I don't love, it does ultimately impact the response body, so I don't think it's semantically incorrect. It also avoids some new protobuf annotation system specific for this use case.

I considered adding this on a service level, but that would impose that all Streaming rpcs within the same service must use identical event and identifier keys.

joroshiba avatar Sep 30 '25 22:09 joroshiba