http-extensions icon indicating copy to clipboard operation
http-extensions copied to clipboard

Resumable upload: feature detection mechanism

Open guoye-zhang opened this issue 3 years ago • 11 comments

Here is a list of various options to perform feature detection for reusable upload. Is 1xx status code the best option among them?

  • HTTP/2 and HTTP/3 SETTINGS frame
  • DNS record
  • OPTIONS request (extra round-trip)
  • /.well-known URI (extra round-trip)

guoye-zhang avatar Sep 04 '22 02:09 guoye-zhang

My 2 cents:

  • I believe this should not rely on techniques specific to certain HTTP versions (thus no to SETTINGS)
  • Requiring access to DNS records will definitively make this hard to deploy
  • We don't need to optimize round-trips in case 1xx doesn't work; that's an incentive to make them work.

That said, it would be good to have a place that documents where servers/clients/frameworks fail to make 1xx work.

reschke avatar Sep 04 '22 09:09 reschke

I went through TIOBE languages list (removed a few obviously inapplicable ones like SQL) and looked up the most common HTTP client libraries in each language. Here is the list of 1xx status code support in each library. I put question marks where I'm not absolutely certain:

  • Python
    • http.client: ignores received 1xx?
  • C
    • curl: supports 1xx
  • Java
    • java.net.HttpURLConnection: ignores received 1xx in latest JDK (20 and aligned back ports), older version (bug) treats 1xx as the final response
    • Apache HttpComponents.HttpClient: (doc) supports 1xx
  • C++
  • C#
    • System.Net.Http: ignores received 1xx?
  • Visual Basic
  • JavaScript
    • Fetch: ignores received 1xx?
  • PHP
  • Objective-C
    • NSURLSession: ignores received 1xx
  • Go
    • Net::HTTP: supports sending, (doc) supports received 1xx through httptrace
  • Delphi
  • Swift
    • URLSession: ignores received 1xx
  • Perl
  • Ruby
    • Net::HTTP: ignores received 1xx?

We can turn this into a wiki page if people want to complete the list.

guoye-zhang avatar Sep 04 '22 20:09 guoye-zhang

Java: as far as I know, Apache HttpClient 5.x does support handling 1xx responses

reschke avatar Sep 05 '22 06:09 reschke

Oh yes, I found the documentation here: https://hc.apache.org/httpcomponents-client-5.1.x/current/httpclient5/apidocs/org/apache/hc/client5/http/async/AsyncExecCallback.html

guoye-zhang avatar Sep 05 '22 06:09 guoye-zhang

For Java's HTTPURLConnection there's even a bug that 1xx is treated as final code, unfixed since being reported in 2016: https://bugs.openjdk.org/browse/JDK-8170305

reschke avatar Sep 06 '22 06:09 reschke

Started test suite at https://github.com/greenbytes/java-http-1xx-tests and verified that at least one client (Apache HC 5) actively supports 1xx codes (when asked nicely).

reschke avatar Sep 06 '22 12:09 reschke

The Go documentation currently says following about 1xx:

supports sending 1xx

Yes, this is supported.

ignores received 1xx?

Not entirely sure on this one. The docs mention that it has a Got1xxResponse callback, but I am not sure to what extend this can currently be used. As per https://pkg.go.dev/net/http:

Responses with status codes in the 1xx range are either handled automatically (100 expect-continue) or ignored. The one exception is HTTP status code 101 (Switching Protocols), which is considered a terminal status and returned by RoundTrip. To see the ignored 1xx responses, use the httptrace trace package's ClientTrace.Got1xxResponse.

Acconut avatar Sep 21 '22 22:09 Acconut

Found the document with some example code at the top: https://pkg.go.dev/net/http/httptrace

guoye-zhang avatar Sep 21 '22 22:09 guoye-zhang

The JDK bugs are now fixed (as of JDK 20); backports pending. Active reporting of 1xx still missing.

reschke avatar Oct 01 '22 12:10 reschke

I have to admit that the state of supporting 1XX in servers and clients is a lot better than anticipated. Do we have any information how support is looking with proxies, such as nginx, HAProxy, and Apache? I think to remember that nginx does not pass on the handling of the Expect: 100-continue header to the downstream server. Or is that not relevant in our case because the server is only interested in sending a 1XX status code and does not have to receive an Expect header? Should we also introduce an Expect: 10?-resumable-upload header (or some similar value)?

So it would also be worth investigating the current state in proxies.

Acconut avatar Oct 01 '22 22:10 Acconut

Discussion on Expect (or not) is in https://github.com/httpwg/http-extensions/issues/2243

LPardue avatar Oct 03 '22 12:10 LPardue

I think there is consensus that an information response is the best approach for a server to indicate its support. There are currently limits to the real-world usability of 1XX responses, but that will improve in the future. As such, I think the question of which mechanism to use for feature detection can be closed. Let me know if we should keep this issue open.

Acconut avatar Nov 05 '22 20:11 Acconut