RFC 9651 Structured Field Values parser, serializer, and conformance toolkit for MoonBit.
| Type | Wire example | BareItem variant |
|---|---|---|
| Integer | 42, -123456789012345 | Integer(Int64) |
| Decimal | 4.5, -0.125 | Decimal(SfDecimal) |
| String | "hello world" | StringItem(String) |
| Token | foo/bar:baz | Token(String) |
| Byte Sequence | :cHJldGVuZCB0aGlzIGlzIGJpbmFyeSBjb250ZW50Lg==: | ByteSequence(Bytes) |
| Boolean | ?1, ?0 | Boolean(Bool) |
| Date | @1659578233 | Date(Int64) |
| Display String | %"hello %c3%a9" | DisplayString(String) |
fn main {
match parse_item("5; foo=bar") {
Err(e) => println(e.to_string())
Ok(item) => {
// item.bare -> Integer(5)
// item.parameters.len() -> 1
// item.parameters.get_by_key("foo") -> Some(Token("bar"))
}
}
}let item = parse_item("5; a=?1; b=?0")?
match serialize_item(item) {
Err(e) => println(e.to_string())
Ok(wire) => println(wire) // "5;a;b=?0" — Boolean true is omitted
}// "0002" -> "2"
// "4.500" -> "4.5"
// "5; a=?1" -> "5;a"
// "1, 42" -> "1, 42"
canonicalize(input, FieldType::List)?match parse_item("abc, def") {
Err(e) => {
e.kind() // SfErrorKind::TrailingInput
e.offset() // 3 — a UTF-8 byte offset into the input
e.to_string() // "trailing input after value at byte 3: near \", def\""
}
Ok(_) => ()
}sfv-tool parse --type item "5; foo=bar"
sfv-tool validate --type list "1, 42"
sfv-tool canonicalize --type dictionary "a=1, b=2;c"
sfv-tool roundtrip --type item "0002"
sfv-tool conformance# check, build, and test on the default target
moon check
moon build
moon test
# test a specific target
moon test --target native
moon test --target js
moon test --target wasm-gc
# run the CLI
moon run cmd/sfv-tool -- --help
# run an example
moon run examples/parse_item
# run the official httpwg conformance suite
moon run cmd/sfv-tool -- conformance
# full verification for all targets (format, build, test, snapshot check)
powershell -ExecutionPolicy Bypass -File scripts/verify_all.ps1pub(all) struct ConformanceStats {
required_valid_total : Int
required_valid_passed : Int
required_invalid_total : Int
required_invalid_passed : Int
canonical_total : Int
canonical_passed : Int
optional_total : Int
optional_passed : Int
optional_failed : Int
expected_total : Int
expected_passed : Int
failures : Array[String]
} derive(Eq, Debug)pub struct Cursor {
input : Bytes
position : Int
}pub enum ExpectedBare {
ExpInteger(Int64)
ExpDecimal(Int64, Int)
ExpString(String)
ExpToken(String)
ExpBinary(String)
ExpBoolean(Bool)
ExpDate(Int64)
ExpDisplayString(String)
}pub enum ExpectedField {
ExpItemField(ExpectedItem)
ExpListField(Array[ExpectedMember])
ExpDictField(Array[(String, ExpectedMember)])
}pub enum ExpectedMember {
ExpItemMember(ExpectedItem)
ExpInnerList(Array[ExpectedItem], Array[ExpectedParam])
}pub struct HttpwgCase {
name : String
header_type : String
raw : Array[String]
must_fail : Bool
can_fail : Bool
canonical : Array[String]?
expected : ExpectedField?
}pub(all) enum SfErrorKind {
UnexpectedEnd
UnexpectedByte(Byte)
InvalidTopLevelType
InvalidKey
InvalidInteger
IntegerOutOfRange
InvalidDecimal
DecimalOutOfRange
InvalidString
InvalidEscape
InvalidToken
InvalidByteSequence
InvalidBase64
InvalidBoolean
InvalidDate
InvalidDisplayString
InvalidPercentEncoding
InvalidUtf8
InvalidParameter
InvalidInnerList
InvalidDictionary
TrailingInput
TooManyMembers
TooManyParameters
InputTooLarge
SerializationError
} derive(Eq, Debug)fn is_base64_char(b : Byte) -> Boolfn is_h_tab(b : Byte) -> Boolfn is_key_char(b : Byte) -> Boolfn is_lower_hex(b : Byte) -> Boolfn is_sp(b : Byte) -> Boolfn is_tchar(b : Byte) -> Boolfn is_visible_ascii(b : Byte) -> Boolfn parse_dictionary_with_limits(input : String, limits : ParseLimits) -> Result[SfDictionary, SfError]fn[T] parse_field_bytes(input : Bytes, limits : ParseLimits, parse_fn : (Cursor, ParseLimits) -> Result[T, SfError]) -> Result[T, SfError]fn parse_integer_or_decimal_cursor(cursor : Cursor, _limits : ParseLimits) -> Result[BareItem, SfError]fn parse_item_or_inner_list_cursor(cursor : Cursor, limits : ParseLimits) -> Result[ListMember, SfError]RFC 9651 Structured Field Values parser, serializer, and conformance toolkit for MoonBit.