Documentation
¶
Overview ¶
Package evaluator contains the pure, per-call JSONata evaluator.
Index ¶
- func DecodeJSON(data []byte) (any, error)
- func DecodeJSONWithOptions(data []byte, options Options) (any, error)
- func Eval(n syntax.Node, input any) (any, error)
- func EvalBindings(n syntax.Node, input any, bindings map[string]any) (any, error)
- func EvalBindingsWithOptions(n syntax.Node, input any, bindings map[string]any, options Options) (any, error)
- func EvalBytesWithOptions(n syntax.Node, data []byte, options Options) (any, error)
- func EvalNoInputBindingsWithOptions(n syntax.Node, bindings map[string]any, options Options) (any, error)
- func EvalNoInputWithOptions(n syntax.Node, options Options) (any, error)
- func EvalStaticComparison(plan *StaticComparisonPlan, input any) (any, bool)
- func EvalStaticComparisonBytes(plan *StaticComparisonPlan, data []byte) (result []byte, ok bool)
- func EvalStaticContains(plan *StaticContainsPlan, input any) (bool, bool)
- func EvalStaticContainsBytes(plan *StaticContainsPlan, data []byte) (bool, bool)
- func EvalStaticDescendantSum(plan *StaticDescendantSumPlan, input any) (any, bool)
- func EvalStaticDescendantSumBytes(plan *StaticDescendantSumPlan, data []byte) ([]byte, bool)
- func EvalStaticExtensionArithmetic(plan *StaticExtensionArithmeticPlan, input any, registry map[string]any) (result any, ok bool, err error)
- func EvalStaticFilterProject(plan *StaticFilterProjectPlan, input any) (any, bool)
- func EvalStaticFilterProjectBytes(plan *StaticFilterProjectPlan, data []byte) ([]byte, bool)
- func EvalStaticMap(plan *StaticMapPlan, input any) (any, bool)
- func EvalStaticMapBytes(plan *StaticMapPlan, data []byte) ([]byte, bool)
- func EvalStaticPath(plan *StaticPathPlan, input any) (result any, ok bool)
- func EvalStaticPathBytes(plan *StaticPathPlan, data []byte) (result []byte, ok bool)
- func EvalStaticSum(plan *StaticSumPlan, input any) (any, bool)
- func EvalStaticSumBytes(plan *StaticSumPlan, data []byte) ([]byte, bool)
- func EvalStaticTransform(plan *StaticTransformPlan, input any) (any, bool)
- func EvalWithOptions(n syntax.Node, input any, options Options) (any, error)
- func IsUndefined(err error) bool
- func NewReflectedExtension(name string, spec ReflectedExtension) (binding any, err error)
- func NormalizeExtensionBinding(input any) any
- func NormalizeExtensionBindingSafe(input any, maxDepth int, check func() error) (any, error)
- type ExtensionArgCountError
- type ExtensionArgTypeError
- type Options
- type ReflectedExtension
- type StaticComparisonPlan
- type StaticContainsPlan
- type StaticDescendantSumPlan
- type StaticExtensionArithmeticPlan
- type StaticFilterProjectPlan
- type StaticMapPlan
- type StaticPathPlan
- type StaticSumPlan
- type StaticTransformPlan
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
func DecodeJSON ¶
func DecodeJSONWithOptions ¶
DecodeJSONWithOptions decodes JSON under the same synchronous runtime controls used by evaluation. Checks run before decoder reads, so a canceled context or exhausted budget stops parsing before the full value is built.
func EvalBindings ¶
EvalBindings evaluates with an isolated binding map. Both "name" and "$name" keys are accepted because fixtures and compatibility callers use both forms.
func EvalBindingsWithOptions ¶
func EvalBytesWithOptions ¶
EvalBytesWithOptions decodes and evaluates with one runtime. Decoded input is already evaluator-owned, so it bypasses the public-input normalization copy while bindings and evaluation continue to share the same budget.
func EvalNoInputWithOptions ¶
EvalNoInputWithOptions evaluates with the JSONata empty input sequence. This is distinct from EvalWithOptions with nil, which represents JSON null.
func EvalStaticComparison ¶
func EvalStaticComparison(plan *StaticComparisonPlan, input any) (any, bool)
EvalStaticComparison returns ok=false whenever normalisation or JSONata sequence semantics could affect the answer. In that case the caller must evaluate the original syntax tree.
func EvalStaticComparisonBytes ¶
func EvalStaticComparisonBytes(plan *StaticComparisonPlan, data []byte) (result []byte, ok bool)
EvalStaticComparisonBytes evaluates the narrow scalar comparison plan on a raw JSON document. Missing, null, container, invalid, and ambiguous values all fall back to the complete evaluator so its sequence and error rules remain authoritative.
func EvalStaticContains ¶
func EvalStaticContains(plan *StaticContainsPlan, input any) (bool, bool)
EvalStaticContains evaluates a decoded input only after validating the complete value graph. Missing, null, containers, non-strings, cycles, unsupported values, non-finite numbers, and over-budget inputs all fall back to the complete evaluator, preserving its public diagnostics.
func EvalStaticContainsBytes ¶
func EvalStaticContainsBytes(plan *StaticContainsPlan, data []byte) (bool, bool)
EvalStaticContainsBytes evaluates a static contains plan over a validated JSON document. The scanner validates the full document, not just the selected path, before attempting the regex shortcut.
func EvalStaticDescendantSum ¶
func EvalStaticDescendantSum(plan *StaticDescendantSumPlan, input any) (any, bool)
EvalStaticDescendantSum evaluates a plan only when every observable value is unambiguous for the ordinary evaluator. Missing fields on descendants are ignored, as they are by the descendant path; no matching numeric field causes fallback so the public undefined result remains available. A matching array, object, nonnumeric value, nonfinite value, or overflow also causes fallback.
func EvalStaticDescendantSumBytes ¶
func EvalStaticDescendantSumBytes(plan *StaticDescendantSumPlan, data []byte) ([]byte, bool)
EvalStaticDescendantSumBytes evaluates a decoded-input descendant sum plan over a validated JSON document.
func EvalStaticExtensionArithmetic ¶
func EvalStaticExtensionArithmetic(plan *StaticExtensionArithmeticPlan, input any, registry map[string]any) (result any, ok bool, err error)
EvalStaticExtensionArithmetic evaluates the plan against an ordinary decoded Go JSON value. ok=false requests the complete evaluator. An error means the fast plan has reached an observable runtime error and must be returned rather than silently changing its semantics.
func EvalStaticFilterProject ¶
func EvalStaticFilterProject(plan *StaticFilterProjectPlan, input any) (any, bool)
EvalStaticFilterProject preserves JSONata's singleton collapse: a single projected match is scalar, while multiple matches are returned as an array at the public boundary. Empty or ambiguous matches use the normal evaluator.
func EvalStaticFilterProjectBytes ¶
func EvalStaticFilterProjectBytes(plan *StaticFilterProjectPlan, data []byte) ([]byte, bool)
EvalStaticFilterProjectBytes evaluates a decoded-input static plan after validating and decoding the complete JSON document. The raw scalar plans have a more direct representation and remain separate from this bridge.
func EvalStaticMap ¶
func EvalStaticMap(plan *StaticMapPlan, input any) (any, bool)
EvalStaticMap returns ok=false whenever JSONata's sequence, undefined, coercion, or diagnostic semantics may be observable. The original AST must be evaluated in those cases.
func EvalStaticMapBytes ¶
func EvalStaticMapBytes(plan *StaticMapPlan, data []byte) ([]byte, bool)
EvalStaticMapBytes evaluates a decoded-input map plan over a validated JSON document.
func EvalStaticPath ¶
func EvalStaticPath(plan *StaticPathPlan, input any) (result any, ok bool)
EvalStaticPath evaluates a plan only when the input shape makes the result unambiguously scalar. A false ok value tells the caller to use the complete evaluator, preserving projections, undefined handling, and ownership rules.
func EvalStaticPathBytes ¶
func EvalStaticPathBytes(plan *StaticPathPlan, data []byte) (result []byte, ok bool)
EvalStaticPathBytes evaluates a static scalar path directly from a JSON document. It returns ok=false for any input whose result cannot be proven to have the same semantics as the normal decoder. Callers must then use the complete evaluator. The scanner validates the complete document, including members unrelated to the selected path.
func EvalStaticSum ¶
func EvalStaticSum(plan *StaticSumPlan, input any) (any, bool)
EvalStaticSum returns ok=false for an empty/missing sequence or whenever a full evaluation may observe a different error or sequence result. This is deliberate: the public fast-path interface cannot represent ErrUndefined, so ambiguous cases must use the original evaluator.
func EvalStaticSumBytes ¶
func EvalStaticSumBytes(plan *StaticSumPlan, data []byte) ([]byte, bool)
EvalStaticSumBytes evaluates a decoded-input sum plan over a validated JSON document.
func EvalStaticTransform ¶
func EvalStaticTransform(plan *StaticTransformPlan, input any) (any, bool)
EvalStaticTransform returns ok=false for any input whose normalization, clone, sequence, diagnostic, or resource semantics could differ. The caller then evaluates the original syntax tree.
func IsUndefined ¶
IsUndefined reports whether an evaluation returned the empty-sequence sentinel. Callers should use this helper instead of comparing error text.
func NewReflectedExtension ¶
func NewReflectedExtension(name string, spec ReflectedExtension) (binding any, err error)
NewReflectedExtension validates and constructs an evaluator binding.
func NormalizeExtensionBinding ¶
NormalizeExtensionBinding converts public extension values to evaluator values while preserving callable values.
func NormalizeExtensionBindingSafe ¶
NormalizeExtensionBindingSafe converts a public extension value while bounding cycles and nesting. Registrations supply a finite check callback; evaluations use the active runtime through normalizeExtensionValue.
Types ¶
type ExtensionArgCountError ¶
ExtensionArgCountError describes a reflected extension arity mismatch.
func (*ExtensionArgCountError) Error ¶
func (e *ExtensionArgCountError) Error() string
type ExtensionArgTypeError ¶
ExtensionArgTypeError describes a reflected extension argument mismatch.
func (*ExtensionArgTypeError) Error ¶
func (e *ExtensionArgTypeError) Error() string
type Options ¶
type Options struct {
Context context.Context
Bindings map[string]any
Timeout time.Duration
Deadline time.Time
MaxCallDepth int
MaxOperations int64
MaxSequenceLength int
Timestamp time.Time
}
Options controls one evaluation without changing the compatibility wrappers. Bindings are copied into the evaluation root and are never retained by the compiled expression. A zero or negative MaxCallDepth or MaxOperations uses the safe runtime default; a positive value sets an explicit limit. A positive MaxSequenceLength enables the JSONata v2.2 sequence guardrail; zero or negative disables it. Timeout values at or below zero are ignored, while a non-zero Deadline is enforced.
type ReflectedExtension ¶
type ReflectedExtension struct {
Func any
UndefinedHandler jtypes.ArgHandler
EvalContextHandler jtypes.ArgHandler
}
ReflectedExtension is the evaluator-facing description of a Go extension. The public jsonata.Extension type is converted to this form at registration.
type StaticComparisonPlan ¶
type StaticComparisonPlan struct {
// contains filtered or unexported fields
}
StaticComparisonPlan describes a scalar field comparison whose operands do not depend on the evaluation environment. The plan is immutable after construction and is safe to share between concurrent evaluations.
func BuildStaticComparisonPlan ¶
func BuildStaticComparisonPlan(n syntax.Node) *StaticComparisonPlan
BuildStaticComparisonPlan recognizes only equality and inequality between a static field path and a scalar literal. All other comparisons use the full evaluator because their coercion and sequence rules are broader.
func (*StaticComparisonPlan) RegistryConflict ¶
func (p *StaticComparisonPlan) RegistryConflict(registry map[string]any) bool
RegistryConflict reports whether a registered name can change the meaning of a field in this plan. Unrelated extensions do not invalidate it.
type StaticContainsPlan ¶
type StaticContainsPlan struct {
// contains filtered or unexported fields
}
StaticContainsPlan describes the only regex shortcut that is safe to use without evaluating the complete expression tree: a field-only path and a parsed regex literal. The regex product is immutable and is shared by all evaluations of the compiled expression.
func BuildStaticContainsPlan ¶
func BuildStaticContainsPlan(n syntax.Node) *StaticContainsPlan
BuildStaticContainsPlan recognises $contains(static.path, /literal/). Function values, string patterns, dynamic paths, and non-literal patterns remain on the normal evaluator path because their coercion and binding rules are observable.
func (*StaticContainsPlan) RegistryConflict ¶
func (p *StaticContainsPlan) RegistryConflict(registry map[string]any) bool
RegistryConflict also covers an override of $contains itself. A registry entry for an unrelated function or field cannot affect this plan.
type StaticDescendantSumPlan ¶
type StaticDescendantSumPlan struct {
// contains filtered or unexported fields
}
StaticDescendantSumPlan describes the narrow decoded-input form $sum(static.path.**.field). It intentionally does not cover bytes input: duplicate JSON object members and source ordering must remain governed by the normal decoder and evaluator.
func BuildStaticDescendantSumPlan ¶
func BuildStaticDescendantSumPlan(n syntax.Node) *StaticDescendantSumPlan
BuildStaticDescendantSumPlan recognises the AST shape of a built-in sum over a recursive descendant path. The plan contains no source text and is immutable after construction.
func (*StaticDescendantSumPlan) RegistryConflict ¶
func (p *StaticDescendantSumPlan) RegistryConflict(registry map[string]any) bool
RegistryConflict reports whether a registered name can alter either the built-in reduction, the static path, or the descendant field lookup.
type StaticExtensionArithmeticPlan ¶
type StaticExtensionArithmeticPlan struct {
// contains filtered or unexported fields
}
StaticExtensionArithmeticPlan describes a narrow arithmetic expression in which both operands are calls to registered functions with scalar input paths. The plan contains AST-derived data only; it does not inspect source text or benchmark case names.
func BuildStaticExtensionArithmeticPlan ¶
func BuildStaticExtensionArithmeticPlan(n syntax.Node) *StaticExtensionArithmeticPlan
BuildStaticExtensionArithmeticPlan recognises expressions such as `$double(value) + $double(offset)`. Calls with dynamic arguments, partial application, or non-named procedures remain on the evaluator path.
func (*StaticExtensionArithmeticPlan) RegistryConflict ¶
func (p *StaticExtensionArithmeticPlan) RegistryConflict(registry map[string]any) bool
RegistryConflict reports only bindings that can shadow one of the input paths. The extension itself is intentionally not treated as a conflict: the current copy-on-write registry snapshot supplies the callable at evaluation time, so re-registration remains visible after compilation.
func (*StaticExtensionArithmeticPlan) RegistryReady ¶
func (p *StaticExtensionArithmeticPlan) RegistryReady(registry map[string]any) bool
RegistryReady reports whether both procedures resolve to callables in the supplied registry snapshot. Builtins and non-callable overrides deliberately fall back to the full evaluator so its name lookup and diagnostics remain authoritative.
type StaticFilterProjectPlan ¶
type StaticFilterProjectPlan struct {
// contains filtered or unexported fields
}
StaticFilterProjectPlan describes the common JSONata shape `items[field = literal].projection`. It deliberately excludes path flattening, dynamic bindings, and all non-scalar intermediate values.
func BuildStaticFilterProjectPlan ¶
func BuildStaticFilterProjectPlan(n syntax.Node) *StaticFilterProjectPlan
BuildStaticFilterProjectPlan recognizes one static equality predicate and a static scalar projection. The AST shape is the selector followed by a path step, which is the parser representation of the documented form.
func (*StaticFilterProjectPlan) RegistryConflict ¶
func (p *StaticFilterProjectPlan) RegistryConflict(registry map[string]any) bool
type StaticMapPlan ¶
type StaticMapPlan struct {
// contains filtered or unexported fields
}
StaticMapPlan describes the narrow AST shape $map(items, function($item){$item.price * $item.quantity}). It is immutable and is used only for ordinary decoded JSON input.
func BuildStaticMapPlan ¶
func BuildStaticMapPlan(n syntax.Node) *StaticMapPlan
BuildStaticMapPlan recognizes one-parameter callbacks whose body is exactly a product of two explicit paths rooted at that callback parameter.
func (*StaticMapPlan) RegistryConflict ¶
func (p *StaticMapPlan) RegistryConflict(registry map[string]any) bool
type StaticPathPlan ¶
type StaticPathPlan struct {
// contains filtered or unexported fields
}
StaticPathPlan is an immutable description of a root field path. It is deliberately narrow: expressions with any dynamic path semantics are not represented and must use the normal evaluator.
func BuildStaticPathPlan ¶
func BuildStaticPathPlan(n syntax.Node) *StaticPathPlan
BuildStaticPathPlan recognizes only a root/context path made from field names. The returned plan owns a copy of all path data and is safe for concurrent use.
func (*StaticPathPlan) RegistryConflict ¶
func (p *StaticPathPlan) RegistryConflict(registry map[string]any) bool
RegistryConflict reports whether a binding can shadow one of the path fields. Unrelated extensions and variables do not affect a static field path and therefore do not disable the plan.
type StaticSumPlan ¶
type StaticSumPlan struct {
// contains filtered or unexported fields
}
StaticSumPlan describes a narrow, immutable reduction over ordinary decoded JSON input. It is intentionally kept separate from the general evaluator: the plan is used only when every value that could affect the result is scalar, finite, and represented by the same JSON-compatible Go types that the normal evaluator accepts.
func BuildStaticSumPlan ¶
func BuildStaticSumPlan(n syntax.Node) *StaticSumPlan
BuildStaticSumPlan recognises only calls to the built-in $sum with a static path, or a static collection selector followed by a scalar path/product. No source-text matching is used: all decisions are made from the parsed AST.
func (*StaticSumPlan) RegistryConflict ¶
func (p *StaticSumPlan) RegistryConflict(registry map[string]any) bool
type StaticTransformPlan ¶
type StaticTransformPlan struct {
// contains filtered or unexported fields
}
StaticTransformPlan describes one deliberately narrow decoded-input transform. It is immutable after compilation and safe to share between concurrent evaluations. Any input or expression shape outside this subset is evaluated by the normal transform implementation.
func BuildStaticTransformPlan ¶
func BuildStaticTransformPlan(n syntax.Node) *StaticTransformPlan
BuildStaticTransformPlan recognizes the frozen medium-transform shape:
$ ~> |collection.path[field = scalar]|{literal, total: left * right}, ["key"]|
The operation must be rooted at the input focus and every name must be a plain field path. In particular, no source-string or benchmark identifier is used to select this plan.
func (*StaticTransformPlan) RegistryConflict ¶
func (p *StaticTransformPlan) RegistryConflict(registry map[string]any) bool
RegistryConflict disables the plan when a registered name can shadow a field lookup or the transform's clone binding. Builtins unrelated to these names cannot alter this plan's meaning.
Source Files
¶
- builtins_collection.go
- builtins_date.go
- builtins_format.go
- builtins_hof.go
- builtins_misc.go
- builtins_regex.go
- builtins_registry.go
- builtins_scalar.go
- builtins_string.go
- date_parse.go
- date_picture.go
- evaluator.go
- extensions.go
- format_integer.go
- format_number.go
- normalization.go
- number_format.go
- phase3.go
- runtime.go
- static_contains.go
- static_descendant_sum.go
- static_extension_arithmetic.go
- static_map.go
- static_path.go
- static_plans.go
- static_raw.go
- static_transform.go