Expand description
§parse_net
The grammar layer for Internet message fields: RFC 9110 field syntax,
media types, RFC 9651 Structured Field Values, HTTP and RFC 5322 dates,
content negotiation, entity tags, ranges, Content-Disposition with
RFC 8187, Cache-Control, Link, Forwarded, authentication challenges,
Host, Origin, and the email lexical layer, with safe writers for each.
Protocol engines (http-net, ws-net, h2-net) frame messages; parse-net reads
what is inside a field value and writes field values back out without ever
emitting CR, LF, or NUL. It is no_std, needs no allocator for any parse,
does no I/O, and has no dependencies.
§Tier 1
The convention in every example is use parse_net as pn;. One plain call
per field:
use parse_net as pn;
// Media types: one strict view, no copy.
let mt = pn::parse_media_type(b"text/html; charset=UTF-8")?;
assert!(mt.essence_is("text/html"));
assert!(mt.charset().is_some_and(|c| c.eq_ignore_ascii_case(b"utf-8")));
// Lists: commas inside quoted strings and comments do not split.
let codings: Vec<&[u8]> = pn::list(b"gzip, deflate;q=0.5, x=\"a,b\"")?.iter().collect();
assert_eq!(codings, [&b"gzip"[..], b"deflate;q=0.5", b"x=\"a,b\""]);
// HTTP-date: all three formats in, IMF-fixdate out.
let now = 1_792_540_800; // the caller's clock, Unix seconds
let d = pn::http_date_at(b"Sunday, 06-Nov-94 08:49:37 GMT", now)?;
assert_eq!(&d.format(), b"Sun, 06 Nov 1994 08:49:37 GMT");
// Host: real IPv4 and IPv6 validation, ports up to 65535.
let hp = pn::parse_host_port(b"[2001:db8::1]:8443")?;
assert_eq!(hp.port, Some(8443));
assert!(pn::parse_host_port(b"127.1").is_err()); // read as IPv4 by browsers: refused
// Writers cannot emit CR, LF, or NUL.
let mut buf = [0u8; 64];
let mut out = pn::SliceSink::new(&mut buf);
pn::media::write("text", "plain", &[("charset", "utf-8")], &mut out)?;
assert_eq!(out.written(), b"text/plain; charset=utf-8");
assert!(pn::write::write_field_value(b"x\r\nSet-Cookie: y", &mut out).is_err());Errors carry a kind and an offset, never input bytes:
use parse_net as pn;
let err = pn::parse_media_type(b"text/ html").unwrap_err();
assert_eq!(err.kind(), pn::ErrorKind::InvalidMediaType);
assert_eq!(err.to_string(), "invalid media type at offset 5");The rest of Tier 1 arrives with 0.4.0 and 0.5.0 (see the
roadmap):
pn::best_media(accept, &["text/html", "application/json"]) // Option<usize>
pn::if_none_match(if_none_match, ¤t_etag)? // bool: answer 304
pn::byte_ranges(range, file_len, &mut buf)? // RangeOutcome
pn::parse_content_disposition(value)?.filename() // prefers filename*
pn::response_cache_control(value)? // ResponseDirectives
pn::client_address(peer, pn::ForwardedSource::XForwardedFor(&lines), &trusted, 16)?
pn::sfv::parse_item(b"same-origin")? // Sec-Fetch-Site
pn::bearer(authorization)? // Option<&[u8]>§Status
Feature complete, 0.5.0: the core, the web layer, links, Structured
Field writing, and the email lexical layer. The public API is written
down in docs/API.md, each field’s grammar in docs/GRAMMAR.md, the
design in dev/PLAN.md, and the milestone schedule in dev/ROADMAP.md
(all in the repository).
Re-exports§
pub use auth::AuthPayload;pub use auth::Challenge;pub use auth::Credentials;pub use auth::basic;pub use auth::bearer;pub use cache::Directive;pub use cache::RequestDirectives;pub use cache::ResponseDirectives;pub use cache::request_cache_control;pub use cache::response_cache_control;pub use date::http_date;stdpub use date::Civil;pub use date::DateFormat;pub use date::HttpDate;pub use date::MailDate;pub use date::http_date_at;pub use disposition::ContentDisposition;pub use disposition::DispositionType;pub use disposition::Filename;pub use disposition::parse_content_disposition;pub use disposition::write_attachment;pub use etag::Condition;pub use etag::EntityTag;pub use etag::TagList;pub use etag::if_match;pub use etag::if_none_match;pub use etag::parse_condition;pub use ext_value::Charset;pub use ext_value::ExtValue;pub use ext_value::write_ext_value;pub use forwarded::ClientAddress;pub use forwarded::ForwardedSource;pub use forwarded::Trust;pub use forwarded::client_address;pub use host::Host;pub use host::HostPort;pub use host::parse_host_port;pub use link::LinkValue;pub use link::Links;pub use link::parse_link;pub use list::List;pub use list::list;pub use media::Boundary;pub use media::MediaRange;pub use media::MediaType;pub use media::parse_media_type;pub use negotiate::QValue;pub use negotiate::best_charset;pub use negotiate::best_encoding;pub use negotiate::best_language;pub use negotiate::best_media;pub use origin::Origin;pub use origin::OriginValue;pub use origin::parse_origin;pub use param::Param;pub use param::Params;pub use range::ByteRange;pub use range::ContentRange;pub use range::IfRange;pub use range::RangeHeader;pub use range::RangeOutcome;pub use range::RangeSpec;pub use range::byte_ranges;pub use text::Comment;pub use text::Quoted;pub use text::Word;pub use write::CountSink;pub use write::Sink;pub use write::SliceSink;
Modules§
- auth
Authorization,Proxy-Authorization,WWW-Authenticate, andProxy-Authenticate(RFC 9110 section 11), with theBearer(RFC 6750) andBasic(RFC 7617) payloads.- cache
Cache-Control(RFC 9111 section 5.2, withimmutablefrom RFC 8246 andstale-while-revalidateandstale-if-errorfrom RFC 5861).- class
- The byte classes of the ABNF, in one table.
- date
- The proleptic Gregorian calendar and HTTP-date (RFC 9110 section 5.6.7).
- disposition
Content-Disposition(RFC 6266, and its use inmultipart/form-datapart headers, RFC 7578 section 4.2).- etag
- Entity tags and the
If-Match/If-None-Matchconditions (RFC 9110 sections 8.8.3 and 13.1). - ext_
value - RFC 8187 extended parameter values:
charset "'" [ language ] "'" value-chars, as infilename*andtitle*. - forwarded
Forwarded(RFC 7239) and the de factoX-Forwarded-For,X-Forwarded-Proto, andX-Forwarded-Host, with client-address resolution through trusted proxies.- host
Host = uri-host [ ":" port ](RFC 9110 section 7.2, citing RFC 3986 section 3.2.2), with real IPv4 and IPv6 validation.- link
Link(RFC 8288 section 3):#link-value, wherelink-value = "<" URI-Reference ">" *( OWS ";" OWS link-param )andlink-param = token BWS [ "=" BWS ( token / quoted-string ) ].- list
- The
#rulelists of RFC 9110 section 5.6.1, including several field lines read as one list (section 5.3). - The email lexical layer (RFC 5322, RFC 2045, RFC 2047, RFC 2231): header lines and folding, encoded words, MIME parameters with continuations, addresses, and message identifiers. The grammar smtp-net needs to write mail and gate-net needs to validate login addresses (D-008); not a mail parser. Charsets decoded: UTF-8, US-ASCII, ISO-8859-1.
- media
- Media types:
type "/" subtype parameters(RFC 9110 section 8.3.1), and the RFC 2046 multipart boundary. - negotiate
- Content negotiation: quality values and the selection of the best offer
for
Accept,Accept-Language,Accept-Encoding, andAccept-Charset(RFC 9110 section 12, RFC 4647). - num
- Decimal digits with overflow checks.
- origin
Origin(RFC 6454 section 7):nullorscheme "://" host [ ":" port ].- param
- Parameters:
*( OWS ";" OWS [ parameter ] )(RFC 9110 section 5.6.6). - pct
- The percent-encoding primitive: validate, decode into a caller buffer, and encode with a named set and hex case.
- range
Range,Content-Range, andIf-Range(RFC 9110 section 14), with resolution against a representation length and budgets against abusive range sets.- scan
- Byte search and field-value validation, eight bytes per step.
- sfv
- Structured Field Values (RFC 9651): Items, Lists, and Dictionaries with every bare item type, parsed into borrowed views.
- text
- The lexical forms of RFC 9110 section 5.6: tokens, optional whitespace,
quoted strings, words (
token / quoted-string), and comments. - write
- Output: the
Sinktrait,SliceSink,CountSink, and the writers for numbers, tokens, quoted strings, parameters, and field values.
Structs§
- Full
- A sink has no room for the bytes it was given.
- Limits
- The work and size bounds every parser enforces.
- Owned
Entity Tag alloc - An owned
EntityTag. - Owned
Host Port alloc - An owned
HostPort. - Owned
Media Type alloc - An owned
MediaType. - Parse
Error - Why a value was refused, and where.
Enums§
- Duplicate
Policy - What a parameter parser does when a name repeats.
- Error
Kind - What a parser refused.
- Write
Error - Why a writer refused.
Constants§
- VERSION
- Crate version string, populated by Cargo at build time.