2.1 Supplements to net/head
These stick with net/head’s respresentation of headers as a
string?, and add a few functions that are "missing" or would
From an HTTP response header, get the HTTP version (such as 1.0 or
1.1), status code number (such as 200), and the status text
description (such as OK).
Convenience wrapper for net/head
whose values are supposed to be a number, such as Content-Length
the header h
extract the value of field
as a number using
. If the field does not exist or its value cannot be converted
to a number, return #f
, but inserts only if field
already exist in h
. Otherwise the field
already present in h
Use case: You want to ensure the header is present, but not disrupt any
existing value—for example, Date or Content-Length.
Combine header fields with the same name into one, with the values as a comma
separated list (with no space between values), as prescribed by RFC 2616,
section 4.2. For example, the two headers x-foo: fred and x-foo:
barney would be combined into the single header x-foo: fred,barney.
Some web services (hello Amazon) require this as part of "signing" a request
for authentication, which means it has to be done exactly right.
Similar to net/head
, but permits
response headers (with their initial status line, such as HTTP/1.1 200
) as well as request headers. Also, if the header is valid and no
exception is thrown, returns h
(making it more convenient to use
this in an expression that both validates and returns a header).
2.2 Heads as a dict
Convert headers represented as a string
of the form
specified in net/head
, to a dict?
where the keys are
and the values are any/c
Specifically, handle the case of duplicate headers. A real-world
example of such duplicate headers is Set-Cookie. Other than
association lists, most types of dicts don’t permit duplicate keys, so
we can’t store duplicate headers using those. Instead, duplicate
headers are stored in the dict under the same key, with the various
values separated by dupe-sep.
> (heads-string->dict "Host: Foo\r\nKey: Value\r\n\r\n") '#hash((Key . "Value") (Host . "Foo"))> (heads-string->dict "Key: Value 1\r\nKey: Value 2\r\n\r\n") '#hash((Key . "Value 1\nValue 2"))
Convert headers represented as a dict?
of the form specified in net/head
the terminating \r\n to end all the headers. This is the reverse of
including its handling of duplicate
> (heads-dict->string '#hash((Key . "Value") (Host . "Foo")))"Host: Foo\r\nKey: Value\r\n\r\n" > (heads-dict->string '((Host . "Foo") (Key . "Value"))) "Host: Foo\r\nKey: Value\r\n\r\n"
, but will set the new value v
only if the key does not already exist in the dict.
> (maybe-dict-set '() 'a "New") '((a . "New")) > (maybe-dict-set '([a . "Old"]) 'a "New") '((a . "Old"))
, but will set the new value for a key only if
the key does not already exist in the dict.