code wiki / (root) / nx_wflow_engine.nx

nx_wflow_engine.nx

buildroot/runtime/nx_wflow_engine.nx

74612 B1566 linesdepth 3pulls 4 transitivereach 33 importersview sourcekind librarytopic wflow
docsdependenciesstructsconstsfunctions

about

nx_wflow_engine.nx -- R1 KEYSTONE of the Workflow Automation ladder (/compare/automation census row "Unified multi-step durable workflow engine"). A WORKFLOW = DATA (law: data as data): flow header = `flowid|event-kind|cond(k=v or -)` step row = `flowid|idx|action|channel-or-dash|arg|max-attempts` (idx 1-based, author ascending) An EVENT = `kind~k=v~...~id=EN` (the nx_crm_flow contract). The engine upgrades nx_crm_flow from single-shot in-memory rules to DURABLE EXECUTION (the Temporal model, sovereign): - every transition is ONE appended line in an append-only RUN LEDGER (flock + O_APPEND, torn-free): `WFRUN rid=<evid>.<flowid> flow=<f> step=<n> status=START|ATT|OK|FAILSTEP|FAILED|DONE att=<k>` - state is DERIVED BY REPLAY of the ledger (event-sourced; nothing mutates, history is sacred) - IDEMPOTENT by construction: a (event id, flow) pair with a START line never starts twice -- the dedup survives crashes/restarts (stronger than the in-memory seen[] of nx_crm_flow) - per-step RETRY up to max-attempts; exhausted -> run FAILED at that step, later steps never run - wf_resume: any run with START but neither DONE nor FAILED (a crash mid-flight) is completed from its first non-OK step; already-OK steps are NOT re-executed (proven in the selftest) ACTIONS v1 (in-process, composing the send plane like nx_crm_flow): create-task | send (any nx_send channel, sr_valid-checked at load) | notify | update-field | probe-fail (DIAGNOSTIC: fails while attempt < arg -- the deterministic retry witness; keep it out of production flows). wf_load validates the WHOLE step set up front (unknown action / bad channel / attempts<1 = LOUD -1, nothing half-loaded). Production ledger path suggestion: knowledge/status/wflow_runs.log. R3 CONNECTOR LAYER (exec-organ): a step can run ANY blessed organ as a workflow step, resolved through a GREEN fail-closed catalog (rows `name<TAB>elf<TAB>GREEN`, the tool_allowlist.conf shape; cx[3]=catalog path, 0=exec-organ refused). Child exit 0 = step OK, nonzero = step fail (so per-step retry applies to REAL organ execution). Production catalog: knowledge/wflow/connectors.conf. PURE CORE (no main -- the house pure-core+gate idiom): gates = _hdl_build/nx_wflow_engine_gate (wf_selftest) + _hdl_build/nx_wflow_connect_gate (connector battery). license_tier: ORIGINAL

dependencies 2 imports · 30 importers

nx_send.nx nx_wflow_text_owned.nx nx_wflow_engine.nx nx_alpha_release_workflow_canonica nx_alpha_release_workflow_gate_t34 nx_wflow_approve_gate.nx nx_wflow_bind_event_gate_t282.nx nx_wflow_bind_event_owned_t282.nx nx_wflow_branch_gate.nx nx_wflow_capacity_canonical_gate_t nx_wflow_capacity_counterexample_t nx_wflow_capture_gate.nx nx_wflow_cli_gate.nx

diagram shows first 10 each side; +0 more imports, +20 more importers in the complete lists below.

imports: nx_send.nxnx_wflow_text_owned.nx

imported by: nx_alpha_release_workflow_canonical_gate_t343.nxnx_alpha_release_workflow_gate_t343.nxnx_wflow_approve_gate.nxnx_wflow_bind_event_gate_t282.nxnx_wflow_bind_event_owned_t282.nxnx_wflow_branch_gate.nxnx_wflow_capacity_canonical_gate_t278.nxnx_wflow_capacity_counterexample_t278.nxnx_wflow_capture_gate.nxnx_wflow_cli_gate.nxnx_wflow_completion_gate_t30.nxnx_wflow_completion_gate_t31.nxnx_wflow_connect_gate.nxnx_wflow_data_gate.nxnx_wflow_diagnostics_gate_t240.nxnx_wflow_diagnostics_t240.nxnx_wflow_engine_gate.nxnx_wflow_evidence_canonical_gate_t230.nxnx_wflow_evidence_gate_t229.nxnx_wflow_foreach_canonical_gate_t278.nxnx_wflow_identity_canonical_selftest_t344.nxnx_wflow_loop_gate.nxnx_wflow_mapping_canonical_gate_t278.nxnx_wflow_obs_gate.nxnx_wflow_onerr_gate.nxnx_wflow_ownership_canonical_gate_t344.nxnx_wflow_result.nxnx_wflow_tpl_gate.nxnx_wflow_var_owned_gate_t277.nxnx_wflow_version_gate.nx

structs

none

consts

27const WF_MAGIC_1089: i64 = 1089
28const WF_MAGIC_65536: i64 = 65536
29const WF_MAGIC_16777216: i64 = 16777216
30const WF_MAGIC_1024: i64 = 1024
31const WF_MAGIC_60000: i64 = 60000
83const WF_EVIDENCE_ERROR: i64 = 0 - 4
109const WF_LEDCAP: i64 = 1048576

functions

34func wf_has(hay: *u8, needle: *u8) -> i64
49func wf_cat(dst: *u8, off: i64, s: *u8) -> i64 { var x: i64 = off; var i: i64 = 0; while s[i] != (0 as u8) { dst[x] = s[i]; x = x + 1; i = i + 1 } return x }
50func wf_catn(dst: *u8, off: i64, v: i64) -> i64
62func wf_atoi(s: *u8) -> i64
78func wf_now() -> i64 { return sys_now_realtime_sec() }
84func wf_append(path: *u8, line: *u8) -> i64
111func wf_evid(ev:*u8,out:*u8,cap:i64)->i64
128func wf_readall(path: *u8, szp: *i64) -> *u8
146func wf_read_snapshot(path:*u8,szp:*i64)->*u8
167func wf_writeall(path: *u8, buf: *u8, n: i64) -> i64
177func wf_has_rng(buf: *u8, ls: i64, le: i64, needle: *u8) -> i64
191func wf_lines_with2(buf: *u8, n: i64, a: *u8, b: *u8) -> i64
203func wf_num_after(buf: *u8, ls: i64, le: i64, key: *u8) -> i64
223func wf_val_after(buf: *u8, ls: i64, le: i64, key: *u8, out: *u8, cap: i64) -> i64
243func wf_max_ok_step(buf: *u8, n: i64, ridtok: *u8) -> i64
259func wf_action_ok(a: *u8) -> i64
271func wf_load(steps: *i64, n: i64) -> i64
360func wf_load_flows(flows: *i64, n: i64) -> i64
372func wf_match(row:*u8,ev:*u8)->i64
379func wf_emit(led: *u8, rid: *u8, fid: *u8, step: i64, st: *u8, att: i64) -> i64
403func wf_conn_resolve(cx: *i64, name: *u8, out: *u8) -> i64
448func wf_rd32(b: *u8, off: i64) -> i64
454func wf_exec_organ(cx: *i64, name0: *u8, arg: *u8, rid: *u8) -> i64
557func wf_emit_iter(led: *u8, rid: *u8, n: i64, val: *u8) -> i64
579func wf_for_each(cx: *i64, chspec: *u8, argraw: *u8, rid: *u8) -> i64
616func wf_exec(cx: *i64, action: *u8, ch: *u8, arg: *u8, att: i64, rid: *u8) -> i64
636func wf_decision(cx: *i64, rid: *u8, idx: i64) -> i64
669func wf_decide(cx: *i64, rid: *u8, idx: i64, decision: *u8, who: *u8) -> i64
698func wf_emit_var(led: *u8, rid: *u8, k: *u8, v: *u8) -> i64
722func wf_val_line_end(buf: *u8, ls: i64, le: i64, key: *u8, out: *u8, cap: i64) -> i64
741func wf_obs_tok_fwd(tok: *u8, rid: *u8) -> i64
750func wf_var_get(cx: *i64, rid: *u8, key: *u8, out: *u8, cap: i64) -> i64
762func wf_subst(cx: *i64, rid: *u8, src: *u8, out: *u8, cap: i64) -> i64
772func wf_bind_event(cx: *i64, rid: *u8, ev: *u8) -> i64
817func wf_defs_version(path: *u8) -> i64
834func wf_emit_ver(led: *u8, rid: *u8, ver: i64) -> i64
849func wf_emit_drift(led: *u8, rid: *u8, ranv: i64, nowv: i64) -> i64
867func wf_run_ver(buf: *u8, n: i64, ridtok: *u8) -> i64
883func wf_tpl_exists(path: *u8) -> i64
889func wf_tpl_path(dir: *u8, name: *u8, ext: *u8, out: *u8) -> i64
899func wf_tpl_index_path(dir: *u8, out: *u8) -> i64
909func wf_tpl_list(dir: *u8) -> i64
954func wf_tpl_indexed(dir: *u8, name: *u8) -> i64
981func wf_tpl_instantiate(dir: *u8, name: *u8, df: *u8, ds: *u8) -> i64
1012func wf_cond_ok(cx: *i64, rid: *u8, cond: *u8) -> i64
1029func wf_run_from(cx: *i64, rid: *u8, fid: *u8, s0: i64) -> i64
1040func wf_run_from_owned(cx: *i64, rid: *u8, fid: *u8, s0: i64, scratch:*WfRunScratch) -> i64
1193func wf_fire(cx:*i64,flows:*i64,nf:i64,ev:*u8)->i64
1202func wf_flow_known(cx:*i64,fid:*u8)->i64
1206func wf_resume(cx:*i64)->i64
1227func wf_lines_load(path: *u8, arr: *i64, cap: i64) -> i64
1255func wf_cx_files(flowsp: *u8, stepsp: *u8, led: *u8, cat: *u8, cx: *i64, flows: *i64) -> i64
1273func wf_fire_files(flowsp: *u8, stepsp: *u8, led: *u8, cat: *u8, ev: *u8) -> i64
1280func wf_resume_files(flowsp: *u8, stepsp: *u8, led: *u8, cat: *u8) -> i64
1289func wf_state_name(st: i64) -> *u8
1296func wf_run_state(buf: *u8, n: i64, tok: *u8) -> i64
1303func wf_obs_runs(buf:*u8,n:i64,rids:*i64,cap:i64)->i64
1314func wf_obs_tok(tok: *u8, rid: *u8) -> i64
1322func wf_obs_release(buf:*u8,n:i64,rids:*i64,slots:i64)->i64
1326func wf_obs_board(led: *u8) -> i64
1367func wf_obs_html(led: *u8, out: *u8) -> i64
1437func wf_selftest() -> i64