Documentation Index
Fetch the complete documentation index at: https://mintlify.com/avsm/httpz/llms.txt
Use this file to discover all available pages before exploring further.
The Etag module provides zero-allocation parsing and comparison for HTTP entity tags per RFC 7232. Entity tags are opaque validators used for conditional requests and cache validation.
Overview
Entity tags (ETags) are identifiers assigned by a server to specific versions of a resource. They enable:
- Cache validation via
If-None-Match (weak comparison)
- Conditional requests via
If-Match (strong comparison)
- Range request validation (requires strong comparison)
ETags come in two varieties:
- Strong:
"xyzzy" - indicates exact content match
- Weak:
W/"xyzzy" - indicates semantic equivalence
Types
Entity Tag
Unboxed entity tag record pointing into the parse buffer.true if tag is weak (prefixed with W/), false for strong tags
Offset of tag content in buffer (after opening quote)
Length of tag content (excluding quotes)
Parse Status
Result status from ETag parsing.Successfully parsed valid ETag
Match Condition
Result of parsing If-Match or If-None-Match header.Value is "*" - matches any entity (use for unconditional requests)
List of entity tags - retrieve with array and count
No valid tags found (malformed header)
Constants
Maximum number of ETags that can be parsed from an If-Match or If-None-Match header.
Empty/invalid ETag constant for initialization.
Parsing Functions
parse
val parse : local_ Base_bigstring.t -> Span.t -> #(status * t)
Parse a single ETag value from a header.
Buffer containing the ETag value (marked as local)
Span indicating the ETag value location in buffer
Returns: Unboxed tuple #(status * t) - tag is only valid if status is Valid.
Accepted formats:
- Strong ETag:
"xyzzy"
- Weak ETag:
W/"xyzzy"
- Empty ETag:
""
Example:
(* Parse ETag header from request *)
let etag_header = Req.find_header req Header_name.Etag in
match etag_header with
| Some span ->
let #(status, etag) = Etag.parse (Req.buf req) span in
(match status with
| Etag.Valid ->
(* Use etag for comparison *)
if Etag.weak_match (Req.buf req) etag current_etag then
(* Resource hasn't changed *)
send_304_not_modified ()
else
send_full_response ()
| Etag.Invalid ->
(* Ignore malformed ETag *)
send_full_response ())
| None ->
send_full_response ()
val parse_match_header
: local_ Base_bigstring.t
-> Span.t
-> t array
-> #(match_condition * int16#)
Parse If-Match or If-None-Match header value. Handles "*" and comma-separated lists of entity tags.
Buffer containing the header value (marked as local)
Span indicating the header value location
Pre-allocated array to store parsed tags (minimum size: max_tags)
Returns: Unboxed tuple #(match_condition * int16#) where:
- First value is the match condition type
- Second value is the count of tags parsed (only valid if condition is
Tags)
Example:
(* Parse If-None-Match for cache validation *)
let if_none_match = Req.find_header req Header_name.If_none_match in
match if_none_match with
| Some span ->
let tags = Array.make (to_int Etag.max_tags) Etag.empty in
let #(condition, count) = Etag.parse_match_header (Req.buf req) span tags in
(match condition with
| Etag.Any ->
(* "*" matches any entity - always modified *)
send_full_response ()
| Etag.Tags ->
(* Check if current ETag matches any in list *)
if Etag.matches_any_weak (Req.buf req) current_etag tags ~count then
(* Resource hasn't changed *)
send_304_not_modified ()
else
send_full_response ()
| Etag.Empty ->
(* No valid tags - ignore header *)
send_full_response ())
| None ->
send_full_response ()
Comparison Functions
strong_match
val strong_match : local_ Base_bigstring.t -> t -> t -> bool
Strong comparison per RFC 7232 Section 2.3.2. Two entity tags are equivalent if:
- Both are not weak (strong tags only)
- Their opaque tag values match character-by-character
Buffer containing both tags (marked as local)
Returns: true if tags match strongly, false otherwise.
Use cases: Range requests, If-Range validation
Example:
(* Validate If-Range for partial content *)
let if_range = Req.find_header req Header_name.If_range in
let can_serve_range = match if_range with
| Some span ->
let #(status, client_etag) = Etag.parse (Req.buf req) span in
status = Etag.Valid &&
Etag.strong_match (Req.buf req) client_etag resource_etag
| None -> false
in
if can_serve_range then
serve_partial_content ()
else
serve_full_content ()
weak_match
val weak_match : local_ Base_bigstring.t -> t -> t -> bool
Weak comparison per RFC 7232 Section 2.3.2. Two entity tags are equivalent if:
- Their opaque tag values match character-by-character
- Regardless of either or both being weak
Buffer containing both tags (marked as local)
Returns: true if tags match weakly, false otherwise.
Use cases: Cache validation, If-None-Match, If-Match
Example:
(* Handle If-None-Match for GET request *)
let handle_if_none_match req current_etag =
match Req.find_header req Header_name.If_none_match with
| Some span ->
let tags = Array.make (to_int Etag.max_tags) Etag.empty in
let #(condition, count) = Etag.parse_match_header (Req.buf req) span tags in
(match condition with
| Etag.Any -> true (* "*" always matches *)
| Etag.Tags -> Etag.matches_any_weak (Req.buf req) current_etag tags ~count
| Etag.Empty -> false)
| None -> false
matches_any_weak
val matches_any_weak : local_ Base_bigstring.t -> t -> t array -> count:int16# -> bool
Check if an ETag matches any in an array using weak comparison.
Buffer containing all tags (marked as local)
Array of tags to compare against
Number of valid tags in the array
Returns: true if etag weakly matches any tag in the array, false otherwise.
matches_any_strong
val matches_any_strong : local_ Base_bigstring.t -> t -> t array -> count:int16# -> bool
Check if an ETag matches any in an array using strong comparison.
Buffer containing all tags (marked as local)
Array of tags to compare against
Number of valid tags in the array
Returns: true if etag strongly matches any tag in the array, false otherwise.
Response Writing
write_etag
val write_etag : Base_bigstring.t -> off:int16# -> t -> local_ Base_bigstring.t -> int16#
Write ETag header to response buffer.
Destination buffer for writing
Current offset in destination buffer
Source buffer containing the tag value (marked as local)
Returns: New offset after writing.
Output format:
- Strong:
ETag: "xyzzy"\r\n
- Weak:
ETag: W/"xyzzy"\r\n
Example:
let off = Res.write_status_line buf ~off 200 in
let off = Etag.write_etag buf ~off resource_etag resource_buf in
let off = Res.write_content_length buf ~off content_len in
let off = Res.crlf buf ~off in
(* ... write body ... *)
write_etag_string
val write_etag_string : Base_bigstring.t -> off:int16# -> weak:bool -> string -> int16#
Write ETag header from string value (allocates for string).
Destination buffer for writing
Current offset in destination buffer
true for weak ETag, false for strong ETag
Tag value (without quotes)
Returns: New offset after writing.
Example:
(* Generate ETag from content hash *)
let content_hash = Digest.string content |> Digest.to_hex in
let off = Res.write_status_line buf ~off 200 in
let off = Etag.write_etag_string buf ~off ~weak:false content_hash in
(* ... continue writing response ... *)
Utility Functions
to_string
val to_string : local_ Base_bigstring.t -> t -> string
Convert ETag to string (allocates). Useful for storage or logging.
Buffer containing the tag value (marked as local)
Returns: String representation of the tag value (without quotes or W/ prefix).
val pp : local_ Base_bigstring.t -> Stdlib.Format.formatter -> t -> unit
Pretty-print ETag in standard format.
Complete Example: Conditional GET
(* Handle conditional GET request with ETag validation *)
let handle_conditional_get req resource =
let buf = Req.buf req in
let resource_etag = resource.etag in (* Pre-computed ETag *)
(* Check If-None-Match (cache validation) *)
let not_modified = match Req.find_header req Header_name.If_none_match with
| Some span ->
let tags = Array.make (to_int Etag.max_tags) Etag.empty in
let #(condition, count) = Etag.parse_match_header buf span tags in
(match condition with
| Etag.Any -> true
| Etag.Tags -> Etag.matches_any_weak buf resource_etag tags ~count
| Etag.Empty -> false)
| None -> false
in
if not_modified then
(* Send 304 Not Modified *)
let off = Res.write_status_line response_buf ~off:(i16 0) 304 in
let off = Etag.write_etag response_buf ~off resource_etag buf in
let off = Res.crlf response_buf ~off in
send_response ~len:off
else
(* Send full 200 response with content *)
let off = Res.write_status_line response_buf ~off:(i16 0) 200 in
let off = Etag.write_etag response_buf ~off resource_etag buf in
let off = Res.write_content_length response_buf ~off
(i64 (Int64.of_int resource.content_length)) in
let off = Res.crlf response_buf ~off in
let off = write_body response_buf ~off resource.content in
send_response ~len:off