Query/evaluation planner for ExDatalog.
The planner sits between the compiled ExDatalog.IR and the evaluation
engine. It produces an ExDatalog.Planner.Plan describing the chosen
strategy, the planned strata, the joins (one per positive body atom), and
the predicates (constraints, aggregates, callbacks).
The planner is intentionally thin in v0.5.0: it wraps the existing IR strata
and classifies body elements. It is the seam through which the :magic_sets
strategy is selected and, in future releases, where join ordering and
cost-based optimization will live.
Strategy selection
plan/2 accepts :strategy (:semi_naive default, or :magic_sets). When
:magic_sets is requested, a :goal option ({relation, pattern}) should be
supplied; otherwise the planner records the strategy but the engine falls back
to semi-naive.
Telemetry
plan/2 emits [:ex_datalog, :planner, :start | :stop | :exception] once per
call (never per rule).
Summary
Functions
Returns a human-readable description of the plan for a program.
Builds an execution Plan from a compiled IR program.
Functions
@spec explain_plan(ExDatalog.Program.t()) :: String.t()
Returns a human-readable description of the plan for a program.
Accepts the same options as plan/2. Validates and compiles the program
first; returns an error string if compilation fails.
Examples
iex> alias ExDatalog.{Program, Rule, Atom, Term, Planner}
iex> program =
...> Program.new()
...> |> Program.add_relation("edge", [:atom, :atom])
...> |> Program.add_relation("path", [:atom, :atom])
...> |> Program.add_rule(
...> Rule.new(
...> Atom.new("path", [Term.var("X"), Term.var("Y")]),
...> [{:positive, Atom.new("edge", [Term.var("X"), Term.var("Y")])}]
...> )
...> )
iex> Planner.explain_plan(program) =~ "Strategy: semi_naive"
true
@spec explain_plan( ExDatalog.Program.t(), keyword() ) :: String.t()
@spec plan( ExDatalog.IR.t(), keyword() ) :: {:ok, ExDatalog.Planner.Plan.t()}
Builds an execution Plan from a compiled IR program.
Options
:strategy—:semi_naive(default) or:magic_sets:goal—{relation, pattern}used whenstrategy: :magic_sets
Returns {:ok, %Plan{}}.
Examples
iex> alias ExDatalog.{Program, Rule, Atom, Term, Compiler, Planner}
iex> {:ok, ir} =
...> Program.new()
...> |> Program.add_relation("edge", [:atom, :atom])
...> |> Program.add_relation("path", [:atom, :atom])
...> |> Program.add_rule(
...> Rule.new(
...> Atom.new("path", [Term.var("X"), Term.var("Y")]),
...> [{:positive, Atom.new("edge", [Term.var("X"), Term.var("Y")])}]
...> )
...> )
...> |> Compiler.compile()
iex> {:ok, plan} = Planner.plan(ir)
iex> plan.strategy
:semi_naive
iex> length(plan.joins)
1