Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Handling of RFC7540 8.1.2.5 #699

Open
valkum opened this issue Jul 6, 2023 · 5 comments
Open

Handling of RFC7540 8.1.2.5 #699

valkum opened this issue Jul 6, 2023 · 5 comments

Comments

@valkum
Copy link

valkum commented Jul 6, 2023

We ran into an issue where the HeaderMap returned in hyper as part of http::Request contains multiple entries for the cookie key.

The HTTP/2 spec states in 8.1.2.5:

If there are multiple Cookie header fields after
decompression, these MUST be concatenated into a single octet string
using the two-octet delimiter of 0x3B, 0x20 (the ASCII string "; ")
before being passed into a non-HTTP/2 context, such as an HTTP/1.1
connection, or a generic HTTP server application.

Currently, If I see this right, during decoding each header is simply appended to the HeaderMap (see https://github.com/hyperium/h2/blob/master/src/frame/headers.rs#L895C38-L895C38)

This HeaderMap ends up in the request that is passed to the user of h2 (/hyper) without merging the Cookie header.
I created a simple repro at https://github.com/valkum/h2-cookie-violation
You need go installed because curl currently does not use 8.1.2.5. but the go http2 seems to do that (similar to Browsers).

If, for any reason, this is an expected deviation from the spec, I guess h2 and possible hyper should get some docs about this deviation. It seems the current ecosystem (for using cookies in Rust) settled on using HeaderMap::get_all for Cookies.

@nox
Copy link
Contributor

nox commented Sep 13, 2023

I don't know if that should be done but at the very least it shouldn't be done by Hyper, as it would be weird for Hyper to do it only for HTTP/2 (as nothing in HTTP/1.1 says they must be concatenated before being passed to other stuff).

I feel like this has already been discussed in the past and the conclusion was that it isn't h2 nor Hyper's business to normalize Cookie headers.

@nox
Copy link
Contributor

nox commented Sep 13, 2023

hyperium/hyper#2528

@valkum
Copy link
Author

valkum commented Sep 13, 2023

Thanks for linking to this in hyper. Would you be open to a PR documenting the behavior somewhere? I am not sure for the best place inside hyper, as hyper::header and hyper::Requestare just re-exports. But as this only affects HTTP/2, I think it makes more sense to document it inside the Inbound Streams block.

@juliuskreutz
Copy link

Hello. Are there any updates on this? Because this unhandled specification has come up in pingora again, since it's using this crate.

Just curious, but shouldn't the h2 crate actually implement all the specifications for HTTP/2 or what was the agreement made here?

@nox
Copy link
Contributor

nox commented Apr 7, 2024

The h2 crate is strictly about HTTP/2, there is no "non-HTTP/2 context, such as an HTTP/1.1 connection, or a generic HTTP server application" here. The place to implement that is in systems that do provide such things, such as Pingora or Hyper.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants