HTTP Selected Headers
MediumParsing · Stripe
Extract selected headers from a raw HTTP request.
request_lines holds the request split into lines. Line 0 is always the request line (for example "GET /v1/charges HTTP/1.1") and is skipped. Header lines follow until the first empty string ""; everything after it (the body) is ignored. wanted lists header names to extract.
Each remaining line is one of:
- Continuation line: starts with a space or tab. It extends the most recent header line. Never treat it as a new header, even if it contains
:. - Header line: contains
:. The name is the text before the first:, trimmed; the value is the text after it. - Malformed line: anything else, or a header line whose trimmed name is empty. It is ignored, and continuation lines right after it are ignored too.
Rules:
- Header names match
wantedcase-insensitively; output names are lowercase. - Normalize every value by trimming it and collapsing runs of spaces/tabs to a single space.
- A continuation line appends its normalized text to the previous header's value, separated by one space (no leading space if the value was empty). Whitespace-only continuations add nothing. Continuations of headers that are not wanted are dropped.
- Repeated headers are reported separately.
Return [lowercase_name, value] pairs for the wanted headers in the order they appear.
Example 1
- Input:
- request_lines = ["POST /v1/charges HTTP/1.1", "Host: api.stripe.com", "Idempotency-Key: abc 123", "X-Trace: part1", "\tpart2 part3", "Content-Type: application/json", "", "{\"amount\": 100}"], wanted = ["idempotency-key", "X-TRACE", "content-type"]
- Output:
- [["idempotency-key", "abc 123"], ["x-trace", "part1 part2 part3"], ["content-type", "application/json"]]
- Explanation
- The request line and
Hostare skipped. The key's value is trimmed and its inner spaces collapsed toabc 123. The tab-indented line continuesX-Trace, givingpart1 part2 part3. Everything after the blank line is body.
Example 2
- Input:
- request_lines = ["GET http://example.com/ HTTP/1.1", "Accept: text/html", " Host: fake", "Host: real.example"], wanted = ["host"]
- Output:
- [["host", "real.example"]]
- Explanation
- The request line contains a colon but is always skipped.
Host: fakestarts with spaces, so it is a continuation ofAccept(which is not wanted) and is dropped rather than read as a header. Only the realHostline is returned.
Example 3
- Input:
- request_lines = ["GET / HTTP/1.1", "Cookie: a=1", "garbage line", " b=2", ": no-name", "cookie: c=3"], wanted = ["cookie"]
- Output:
- [["cookie", "a=1"], ["cookie", "c=3"]]
- Explanation
garbage linehas no colon, so it is malformed and the continuationb=2after it is ignored.: no-namehas an empty name. The two cookie headers are returned separately, in order.
Constraints
1 <= request_lines.length <= 10^50 <= wanted.length <= 100- Lines contain printable ASCII characters, spaces, and tabs