@weavejester I'm implementing a new clojure web server and naturally want to fully support ring. However I am also drawn towards implementing a parallel interface like https://github.com/http-kit/http-kit/blob/016e77141e600fe9068dc1ac091f758e760914dd/src/org/httpkit/server.clj#L256-L303for async http responses (not websockets, and without the cruft underneath) primarily because of the on-close callback feature.
An app server that is streaming a response with StreamableResponseBody cannot know the connection is closed until it attempts to write to the stream. In applications with long lived SSE streams this is a deal breaker, as the server wants to cleanup any resources dedicated to the stream as soon as it can.
Has this come up before? Is there any appetite to address it?
It's come up before, and I'm happy to consider an extension for it. Most likely this would come in the form of an additional protocol that could be added to relevant body types.
Hello! If I may chime in, I would like to see something like that making it into the spec. The on-close callback feature makes working with SSE streams a lot nicer. Beyond Http-kit I know Aleph allows for the body of a response to be a manifold stream and I believe there is a similar on-close callback feature there.
Alright, good to know. Shall I open a discussion/exploration issue in github like I did for 103 early hints?
for posterity https://github.com/ring-clojure/ring/issues/542 will continue the discussion there, 🙏
Thanks for the issue. Out of interest, are you writing a wrapper around an existing HTTP server or writing one from scratch?
Oh I wish I could write one from scratch. http/1 is easy enough, even http/2 with more effort, but implementing http/3 without a supporting TLS and QUIC stack already (which we don't have on the JVM yet) is, imo, beyond a one person maintainer amount of work. That requires large commercial support. I'm wrapping an existing server: libh2o, which powers h2o, the web server used by fastly. It's written in C, so my adapter uses panama ffi/ffm. It'll support h1-h3, automatic https (acme out of the box), 103 early hints, web transport, etc.
@ramblurr Is there any publicly accessible link to your libh2o wrapper work?
thanks for the interest @kumarshantanu It's not yet public, it's still under development. The basics are there (http1/2, ring adapter, early hints) but I'm still hacking on auto https and http3. I'll drop a ping here once I make it public.
Thanks for the explanation. My usual setup is to run HTTP/1.1 on the server and let the reverse proxy handle HTTP/2 and 3 support.
Yea, that is definitely the norm. But I find that reducing infrastructure complexity goes a long way in the types of projects I'm involved with. So having a single deployment artifact for the application, that includes the web server is a really big win. And for apps that use in-process databases like sqlite, all you need is an uberjar and a systemd unit file on a linux box to deploy.
Then there's the fact that request smuggling and http desync attacks are really starting to take off. And those sorts of attacks target the reverse proxy + http/1.1 application server. Using http/2 between the reverse proxy and the application can mitigate desync attacks dramatically.