DOC_INDEX
THEME
DOCS/Specification/Expression Playground (orchstep eval)

Expression Playground (orchstep eval)

Evaluate template and JavaScript expressions against a real workflow context - without running any steps

Available since v0.8.0.

orchstep eval answers one question instantly: "what value would this expression have in my workflow, with these exact flags?" It builds the same variable context orchstep run would - workflow defaults, environment groups/environments, --vars-file, --var - then evaluates your expression against it. No steps execute; nothing is touched.

It replaces the debug loop of adding a throwaway echo step and running the task just to see what a variable resolves to.

Quick examples

All outputs below are real, from the environment-promotion use case:

$ orchstep eval --env production 'vars.db_host'
prod-db.internal:5432

$ orchstep eval --env production --var replicas=99 '{{ vars.replicas }}'
99

$ orchstep eval --env production 'vars.require_approval === "true" && Number(vars.replicas) > 4'
true

$ orchstep eval --env staging --lang template 'deploying {{ vars.app_name }} to {{ vars.env_name }} ({{ vars.replicas }} replicas)'
deploying checkout-service to staging (4 replicas)

$ orchstep eval --env dev '({host: vars.db_host, level: vars.log_level})'
{
  "host": "dev-db.internal:5432",
  "level": "debug"
}

Objects print as JSON; scalars print plainly. Evaluation errors surface exactly as they would in a workflow (and exit non-zero):

$ orchstep eval 'vars.nonexistent.deep'
Error: failed to evaluate JavaScript expression: TypeError: Cannot read property 'deep' of undefined

Flags

FlagDescription
-f, --fileWorkflow file providing the context (default: orchstep.yml if present)
--envEnvironment to apply, exactly like run
--varRuntime variable overrides (repeatable, highest precedence)
--vars-fileLoad variables from a YAML file
--langauto (default), template, or js
-q, --quietPrint only the value

Without a workflow file it still works as a bare calculator (orchstep eval '1 + 2 * 3' prints 7) - with a note that the context is empty.

Language selection

auto applies the engine's own condition rule: input fully wrapped in {{ }} evaluates as a Go template, anything else as JavaScript - the identical behavior of if: and assert. Two overrides:

  • --lang template renders the input through the template pipeline, so mixed text works ('host={{ vars.db_host }}') - the same rendering do: and args: get.
  • --lang js forces JavaScript.

Interactive REPL

orchstep eval with no expression (in a terminal) starts a REPL:

$ orchstep eval -f orchstep.yml --env staging
orchstep eval - interactive expression playground
eval(auto)> vars.replicas
[javascript] 4 (truthy=true)
eval(auto)> {{ vars.db_host }}
[template] staging-db.internal:5432 (truthy=true)
eval(auto)> :vars        # dump the full merged variable map as JSON
eval(auto)> :tpl         # switch language (:js, :auto)
eval(auto)> :q

Why results can't lie

eval is not a reimplementation - it calls the engine's own evaluation paths (the same condition evaluator and template pipeline workflows use). Whatever it prints is what your if:, assert, until: or {{ }} will do at run time, byte for byte.

See also