String Capture Patterns

This example first extracts a filename from a path such as notes/todo.txt, then captures and parses a numeric user ID from a path such as users/42. String capture patterns let us match the fixed parts of each string and give the variable part a name.


filename : Str -> Try(Str, [InvalidPath])
filename = |path| match path {
	"notes/${name}.txt" => Ok(name)
	_ => Err(InvalidPath)
}

expect filename("notes/todo.txt") == Ok("todo")
expect filename("notes/todo.csv") == Err(InvalidPath)

route : Str -> Try(U64, [NotFound, InvalidId])
route = |path| match path {
	"users/${id}" => U64.from_str(id).map_err(|_| InvalidId)
	_ => Err(NotFound)
}

expect route("users/42") == Ok(42)
expect route("users/alice") == Err(InvalidId)
expect route("posts/42") == Err(NotFound)

Captured values are strings: filename returns the captured name directly, while route uses U64.from_str to convert the captured ID into a number. A matching path with an invalid ID returns InvalidId; a path that does not match users/${id} returns NotFound.

Output

Run this from the directory that has main.roc in it:

$ roc test main.roc

All (5) tests passed in 9.8 ms.

Validated with Roc nightly-2026-10-29-a0a9fc2.