party

Party: A simple parser combinator library Party is pre-alpha and breaking changes should be expected in the near future.

Types

The custom error type for the parser, which can itself be parameterized by a user-defined error type The user-defined error type is useful for, for example, adding a int.parse call into your parser pipeline

pub type ParseError(e) {
  Unexpected(error: String)
  UserError(error: e)
}

Constructors

  • Unexpected(error: String)
  • UserError(error: e)

The parser type, parameterized by the type it parses and the user-defined error type it can return

pub opaque type Parser(a, e)

Functions

pub fn alphanum() -> Parser(String, a)

parse an alphanumeric character

pub fn alt(p: Parser(a, b), q: Parser(a, b)) -> Parser(a, b)

parse the first parser, or the second if the first fails

pub fn char(c: String) -> Parser(String, a)

parse a specific character

pub fn choice(ps: List(Parser(a, b))) -> Parser(a, b)

parse with the first parser in the list that doesn’t fail

pub fn digit() -> Parser(String, a)

parse a digit

pub fn do(p: Parser(a, b), f: fn(a) -> Parser(c, b)) -> Parser(
  c,
  b,
)

a monadic bind for pleasant interplay with gleam’s use syntax. example:

fn identifier() -> Parser(String, e) {
    use first <- do(lowercase_letter())
    use rest <- do(many(alt(alphanum(), char("_"))))
    return(first <> string.concat(rest))
}
pub fn error_map(p: Parser(a, b), f: fn(b) -> c) -> Parser(a, c)

transform the user-defined error type with a user-provided conversion function

pub fn go(p: Parser(a, b), src: String) -> Result(
  a,
  ParseError(b),
)

user-facing run

pub fn lazy(p: fn() -> Parser(a, b)) -> Parser(a, b)

run a parser as normal, but the parser itself isn’t evaluated until it is used. This is needed for recursive grammars, such as E := n | E + E where n is a number. example: lazy(digit) instead of digit()

pub fn letter() -> Parser(String, a)

parse a lowercase or uppercase letter

pub fn lowercase_letter() -> Parser(String, a)

parse a lowercase letter

pub fn many(p: Parser(a, b)) -> Parser(List(a), b)

keep trying the parser until it fails, and return the array of parsed results. This cannot fail because it parses zero or more times!

pub fn many1(p: Parser(a, b)) -> Parser(List(a), b)

keep trying the parser until it fails, and return the array of parsed results. This can fail, because it must parse successfully at least once!

pub fn map(p: Parser(a, b), f: fn(a) -> c) -> Parser(c, b)

do p, then apply f to the result if it succeeded

pub fn perhaps(p: Parser(a, b)) -> Parser(Result(a, Nil), b)

try running a parser, but still succeed (with Error(Nil)) if it failed

pub fn pos() -> Parser(Int, a)
pub fn return(x: a) -> Parser(a, b)

a monadic return for pleasant interplay with gleam’s use syntax. see do for more details and an example. This is redundant if the last do is a map instead. But I prefer using it, stylistically.

pub fn satisfy(when pred: fn(String) -> Bool) -> Parser(String, a)

parse a character if it matches the predicate

pub fn seq(p: Parser(a, b), q: Parser(c, b)) -> Parser(c, b)

do the first parser, ignore its result, then do the second parser

pub fn try(p: Parser(a, b), f: fn(a) -> Result(c, b)) -> Parser(
  c,
  b,
)

do p, the apply f to the result if it succeeded. f itself can fail with the user-defined error type, and if it does the result is a UserError with the error.

pub fn uppercase_letter() -> Parser(String, a)

parse an uppercase letter

Search Document