07 · Pattern Matching
First-class capture patterns
Store a pat literal as a reusable value. Its parse method returns Result with an exact typed capture record. Input mismatch and failed conversions return structured errors. Construction retains conversion functions without running their validation predicates.
On this page
Store a pat literal as a reusable value. Its parse method returns Result with an exact typed capture record. Input mismatch and failed conversions return structured errors. Construction retains conversion functions without running their validation predicates.
Complete example
First-class capture patterns.
first-class-capture-patterns.zolo
// Exact public capture record; construction performs no parse or validation.
var input_calls = 0
fn input() -> str { input_calls += 1; "users/9223372036854775807/false" }
let route = pat"users/{id: int}/{ready: bool}"
let captured = route.parse(input()).unwrap()
print(captured.id)
print(captured.ready)
print(input_calls)
print(route.parse("prefix/users/1/true").is_err())
print(route.parse("users/9223372036854775808/true").is_err())
print(route.parse("users/1/true/trailing").is_err())
match route.parse("users/nope/true") {
.Err(error) => { print(error.kind); print(error.input) },
.Ok(_) => print("unexpected"),
}
let id = "outer"
let empty = pat""
print(empty.parse("").is_ok())
print(empty.parse("x").is_err())
let escaped = pat"{{literal}}/{id: str}"
print(escaped.parse(r"{literal}/é中😀").unwrap().id)
print(id)
newtype Positive(int) where |n| n > 0
let positive = pat"n/{value: Positive}"
print(positive.parse("n/3").unwrap().value.unwrap())
print(positive.parse("n/-1").is_err())
var cleanup = ""
struct ScopeResource {}
impl core::cleanup::Cleanup for ScopeResource { fn close(self) { cleanup += "closed" } }
using resource = ScopeResource {} {
let parsed = route.parse("bad")
defer { cleanup += "defer/" }
print(parsed.is_err())
}
print(cleanup)
fn parse_with_cleanup() -> Result<int, { kind: str, input: str, pattern: str }> {
using resource = ScopeResource {} {
defer { cleanup += "defer/" }
let args = route.parse("bad")?;
.Ok(args.id)
}
}
cleanup = ""
print(parse_with_cleanup().is_err())
print(cleanup)
var construction_calls = 0
fn make_route() { construction_calls += 1; pat"users/{id: int}" }
print(make_route().parse("users/8").unwrap().id)
print(construction_calls)
Rules and behavior
Validation, schemas and units · Documentation
From a checkout of the repository:
zolo examples/features/first-class-capture-patterns.zolo
See also