Chronix.Grammar (Chronix v0.2.0)

Copy Markdown View Source

NimbleParsec grammar for Chronix expressions.

This module compiles into the core parsers used by Chronix.Time, Chronix.Duration, and Chronix.Parser. Each of those modules is a thin façade that invokes a defparsec defined here and post-processes the AST for its own public contract via Chronix.Evaluator.

The public API remains on the façade modules; nothing here is intended for direct use by callers of Chronix.

AST shapes

Time (:time):

  • :noon, :midnight
  • {:time_12h, keyword_list} — e.g. [hour: 3, minute: 15, meridiem: :pm]
  • {:time_24h, keyword_list} — e.g. [hour: 15, minute: 30, second: 45]

Duration (:duration):

  • {:future_shift, [number, {base_unit, multiplier}]}
  • {:past_shift, [number, {base_unit, multiplier}]}
  • {:next_period, [:week | :month | :year]}

  • {:last_period, [:week | :month | :year]}

  • {:next_weekday, [atom | {:unknown_weekday, str}]}

  • {:last_weekday, [atom | {:unknown_weekday, str}]}

  • {:upcoming_weekday, [atom | {:unknown_weekday, str}]}this/on

  • :in_ago_error
  • Inside shifts, unknown numbers/units: {:unknown_number, str}, {:unknown_unit, str}

Expression (:expression):

  • :now — now
  • {:day_offset, n} — today (0)/tomorrow/yesterday/day-after/day-before
  • {:this_period, :week | :month | :year}

  • :tonight, :last_night
  • {:this_tod, %Time{}}, {:tomorrow_tod, %Time{}}, {:yesterday_tod, %Time{}}
  • {:at_time, [time_ast]}
  • {:year_first_date, [year, month, day]}
  • {:year_last_date, [a, b, year]}
  • {:beginning_of, [duration_ast]}, {:end_of, [duration_ast]}
  • Duration and Time AST shapes (passed through)

Custom errors from post_traverse are wrapped as {:chronix_error, reason} to distinguish them from generic grammar-mismatch failures.

Summary

Functions

Parses the given binary as duration.

Parses the given binary as expression.

Parses the given binary as time.

Functions

duration(binary, opts \\ [])

@spec duration(binary(), keyword()) ::
  {:ok, [term()], rest, context, line, byte_offset}
  | {:error, reason, rest, context, line, byte_offset}
when line: {pos_integer(), byte_offset},
     byte_offset: non_neg_integer(),
     rest: binary(),
     reason: String.t(),
     context: map()

Parses the given binary as duration.

Returns {:ok, [token], rest, context, position, byte_offset} or {:error, reason, rest, context, line, byte_offset} where position describes the location of the duration (start position) as {line, offset_to_start_of_line}.

To column where the error occurred can be inferred from byte_offset - offset_to_start_of_line.

Options

  • :byte_offset - the byte offset for the whole binary, defaults to 0
  • :line - the line and the byte offset into that line, defaults to {1, byte_offset}
  • :context - the initial context value. It will be converted to a map

expression(binary, opts \\ [])

@spec expression(binary(), keyword()) ::
  {:ok, [term()], rest, context, line, byte_offset}
  | {:error, reason, rest, context, line, byte_offset}
when line: {pos_integer(), byte_offset},
     byte_offset: non_neg_integer(),
     rest: binary(),
     reason: String.t(),
     context: map()

Parses the given binary as expression.

Returns {:ok, [token], rest, context, position, byte_offset} or {:error, reason, rest, context, line, byte_offset} where position describes the location of the expression (start position) as {line, offset_to_start_of_line}.

To column where the error occurred can be inferred from byte_offset - offset_to_start_of_line.

Options

  • :byte_offset - the byte offset for the whole binary, defaults to 0
  • :line - the line and the byte offset into that line, defaults to {1, byte_offset}
  • :context - the initial context value. It will be converted to a map

time(binary, opts \\ [])

@spec time(binary(), keyword()) ::
  {:ok, [term()], rest, context, line, byte_offset}
  | {:error, reason, rest, context, line, byte_offset}
when line: {pos_integer(), byte_offset},
     byte_offset: non_neg_integer(),
     rest: binary(),
     reason: String.t(),
     context: map()

Parses the given binary as time.

Returns {:ok, [token], rest, context, position, byte_offset} or {:error, reason, rest, context, line, byte_offset} where position describes the location of the time (start position) as {line, offset_to_start_of_line}.

To column where the error occurred can be inferred from byte_offset - offset_to_start_of_line.

Options

  • :byte_offset - the byte offset for the whole binary, defaults to 0
  • :line - the line and the byte offset into that line, defaults to {1, byte_offset}
  • :context - the initial context value. It will be converted to a map