@probelabs/visor 0.1.124 → 0.1.126
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/config.d.ts.map +1 -1
- package/dist/docs/DEPLOYMENT.md +117 -11
- package/dist/docs/GITHUB_CHECKS.md +18 -4
- package/dist/docs/NPM_USAGE.md +112 -39
- package/dist/docs/action-reference.md +63 -9
- package/dist/docs/advanced-ai.md +58 -51
- package/dist/docs/ai-configuration.md +99 -11
- package/dist/docs/ai-custom-tools-usage.md +70 -33
- package/dist/docs/ai-custom-tools.md +50 -27
- package/dist/docs/architecture.md +1232 -0
- package/dist/docs/bot-transports-rfc.md +13 -3
- package/dist/docs/ci-cli-mode.md +116 -8
- package/dist/docs/claude-code.md +111 -41
- package/dist/docs/command-provider.md +37 -15
- package/dist/docs/commands.md +252 -6
- package/dist/docs/configuration.md +138 -4
- package/dist/docs/contributing.md +737 -0
- package/dist/docs/custom-tools.md +39 -8
- package/dist/docs/dashboards/README.md +33 -19
- package/dist/docs/debug-visualizer-progress.md +14 -13
- package/dist/docs/debug-visualizer-rfc.md +14 -13
- package/dist/docs/debug-visualizer.md +30 -5
- package/dist/docs/debugging.md +73 -8
- package/dist/docs/default-output-schema.md +24 -20
- package/dist/docs/dependencies.md +75 -21
- package/dist/docs/dev-playbook.md +85 -9
- package/dist/docs/engine-pause-resume-rfc.md +11 -11
- package/dist/docs/engine-state-machine-plan.md +10 -3
- package/dist/docs/event-driven-github-integration-rfc.md +20 -11
- package/dist/docs/event-triggers.md +95 -6
- package/dist/docs/execution-statistics-rfc.md +16 -4
- package/dist/docs/fact-validator-gap-analysis.md +12 -1
- package/dist/docs/fact-validator-implementation-plan.md +19 -11
- package/dist/docs/fail-if.md +116 -11
- package/dist/docs/failure-conditions-implementation.md +40 -6
- package/dist/docs/failure-conditions-schema.md +243 -87
- package/dist/docs/failure-routing-rfc.md +43 -18
- package/dist/docs/failure-routing.md +80 -23
- package/dist/docs/faq.md +836 -0
- package/dist/docs/foreach-dependency-propagation.md +32 -15
- package/dist/docs/github-ops.md +6 -5
- package/dist/docs/glossary.md +322 -0
- package/dist/docs/goto-forward-run-plan.md +23 -10
- package/dist/docs/guides/criticality-modes.md +15 -13
- package/dist/docs/guides/fault-management-and-contracts.md +8 -5
- package/dist/docs/guides/workflow-style-guide.md +17 -8
- package/dist/docs/http.md +102 -3
- package/dist/docs/human-input-provider.md +20 -36
- package/dist/docs/index.md +206 -0
- package/dist/docs/lifecycle-hooks.md +322 -2
- package/dist/docs/limits.md +20 -5
- package/dist/docs/liquid-templates.md +86 -14
- package/dist/docs/loop-routing-refactor.md +4 -2
- package/dist/docs/mcp-provider.md +53 -19
- package/dist/docs/mcp.md +27 -1
- package/dist/docs/memory.md +7 -2
- package/dist/docs/migration.md +596 -0
- package/dist/docs/observability.md +227 -6
- package/dist/docs/output-formats.md +388 -9
- package/dist/docs/output-history.md +36 -6
- package/dist/docs/performance.md +510 -4
- package/dist/docs/pluggable.md +95 -4
- package/dist/docs/proposals/snapshot-scope-execution.md +6 -5
- package/dist/docs/providers/git-checkout.md +16 -14
- package/dist/docs/providers/noop.md +696 -0
- package/dist/docs/recipes.md +8 -9
- package/dist/docs/rfc/git-checkout-step.md +3 -1
- package/dist/docs/rfc/on_init-hook.md +18 -5
- package/dist/docs/rfc/workspace-isolation.md +16 -0
- package/dist/docs/roadmap/criticality-implementation-tasks.md +27 -27
- package/dist/docs/router-patterns.md +155 -43
- package/dist/docs/schema-templates.md +51 -15
- package/dist/docs/script.md +162 -13
- package/dist/docs/sdk.md +46 -12
- package/dist/docs/security.md +464 -5
- package/dist/docs/slack-integration.md +481 -0
- package/dist/docs/tag-filtering.md +60 -20
- package/dist/docs/telemetry-setup.md +157 -46
- package/dist/docs/test-framework-rfc.md +37 -36
- package/dist/docs/testing/assertions.md +92 -4
- package/dist/docs/testing/ci.md +56 -7
- package/dist/docs/testing/cli.md +57 -15
- package/dist/docs/testing/cookbook.md +53 -20
- package/dist/docs/testing/dsl-reference.md +110 -9
- package/dist/docs/testing/fixtures-and-mocks.md +28 -3
- package/dist/docs/testing/flows.md +59 -4
- package/dist/docs/testing/getting-started.md +14 -13
- package/dist/docs/testing/troubleshooting.md +39 -2
- package/dist/docs/timeouts.md +174 -18
- package/dist/docs/troubleshooting.md +176 -6
- package/dist/docs/workflow-creation-guide.md +101 -3
- package/dist/docs/workflows.md +138 -41
- package/dist/examples/README.md +169 -4
- package/dist/examples/ai-custom-tools-simple.yaml +2 -3
- package/dist/examples/cron-webhook-config.yaml +15 -0
- package/dist/examples/forEach-example.yaml +6 -0
- package/dist/examples/git-checkout-basic.yaml +4 -0
- package/dist/examples/git-checkout-compare.yaml +6 -0
- package/dist/examples/git-checkout-cross-repo.yaml +7 -0
- package/dist/examples/http-integration-config.yaml +30 -0
- package/dist/examples/https-server-config.yaml +15 -0
- package/dist/examples/mcp-provider-example.yaml +10 -10
- package/dist/examples/transform-example.yaml +3 -0
- package/dist/examples/webhook-pipeline-config.yaml +18 -0
- package/dist/examples/workflows/workflow-composition-example.yaml +4 -0
- package/dist/frontends/slack-frontend.d.ts +2 -0
- package/dist/frontends/slack-frontend.d.ts.map +1 -1
- package/dist/generated/config-schema.d.ts +11 -7
- package/dist/generated/config-schema.d.ts.map +1 -1
- package/dist/generated/config-schema.json +11 -7
- package/dist/index.js +3127 -974
- package/dist/output/traces/{run-2026-01-28T16-15-24-569Z.ndjson → run-2026-01-31T16-37-22-321Z.ndjson} +84 -84
- package/dist/output/traces/{run-2026-01-28T16-16-09-757Z.ndjson → run-2026-01-31T16-38-06-031Z.ndjson} +1013 -1013
- package/dist/providers/ai-check-provider.d.ts +9 -2
- package/dist/providers/ai-check-provider.d.ts.map +1 -1
- package/dist/providers/command-check-provider.d.ts.map +1 -1
- package/dist/providers/mcp-custom-sse-server.d.ts +17 -1
- package/dist/providers/mcp-custom-sse-server.d.ts.map +1 -1
- package/dist/providers/workflow-check-provider.d.ts.map +1 -1
- package/dist/providers/workflow-tool-executor.d.ts +68 -0
- package/dist/providers/workflow-tool-executor.d.ts.map +1 -0
- package/dist/sdk/{check-provider-registry-AQ3JETBG.mjs → check-provider-registry-3KI5RKXT.mjs} +6 -5
- package/dist/sdk/check-provider-registry-IYILYY35.mjs +28 -0
- package/dist/sdk/chunk-2CPMMNIX.mjs +1459 -0
- package/dist/sdk/chunk-2CPMMNIX.mjs.map +1 -0
- package/dist/sdk/chunk-5LI6T4O3.mjs +3600 -0
- package/dist/sdk/chunk-5LI6T4O3.mjs.map +1 -0
- package/dist/sdk/{chunk-YLQ4UN62.mjs → chunk-A4PGHURG.mjs} +6838 -6257
- package/dist/sdk/chunk-A4PGHURG.mjs.map +1 -0
- package/dist/sdk/chunk-EXFGO4FX.mjs +147 -0
- package/dist/sdk/chunk-EXFGO4FX.mjs.map +1 -0
- package/dist/sdk/chunk-PJ7K5UFC.mjs +17732 -0
- package/dist/sdk/chunk-PJ7K5UFC.mjs.map +1 -0
- package/dist/sdk/{chunk-BHZ4CKUS.mjs → chunk-PXFIALUH.mjs} +77 -8
- package/dist/sdk/chunk-PXFIALUH.mjs.map +1 -0
- package/dist/sdk/{chunk-PVITVJ6J.mjs → chunk-RTKJXNZS.mjs} +32 -9
- package/dist/sdk/chunk-RTKJXNZS.mjs.map +1 -0
- package/dist/sdk/chunk-VW2GBXQT.mjs +606 -0
- package/dist/sdk/chunk-VW2GBXQT.mjs.map +1 -0
- package/dist/sdk/{config-RQQPMLRD.mjs → config-5AUYQFHE.mjs} +2 -2
- package/dist/sdk/config-6CUVEH7H.mjs +16 -0
- package/dist/sdk/config-6CUVEH7H.mjs.map +1 -0
- package/dist/sdk/{github-frontend-6Q4BISZX.mjs → github-frontend-BZ4N3BFZ.mjs} +7 -3
- package/dist/sdk/github-frontend-BZ4N3BFZ.mjs.map +1 -0
- package/dist/sdk/host-4MT3EW2I.mjs +52 -0
- package/dist/sdk/{host-P5NQICP7.mjs → host-NYWXLIFC.mjs} +2 -2
- package/dist/sdk/host-NYWXLIFC.mjs.map +1 -0
- package/dist/sdk/{routing-DEY2AIXM.mjs → routing-6R42GXUO.mjs} +2 -2
- package/dist/sdk/routing-6R42GXUO.mjs.map +1 -0
- package/dist/sdk/routing-7FXPULTO.mjs +24 -0
- package/dist/sdk/routing-7FXPULTO.mjs.map +1 -0
- package/dist/sdk/sdk.d.mts +3 -1
- package/dist/sdk/sdk.d.ts +3 -1
- package/dist/sdk/sdk.js +12163 -11204
- package/dist/sdk/sdk.js.map +1 -1
- package/dist/sdk/sdk.mjs +14 -10
- package/dist/sdk/sdk.mjs.map +1 -1
- package/dist/sdk/slack-frontend-JUT3TYVC.mjs +821 -0
- package/dist/sdk/slack-frontend-JUT3TYVC.mjs.map +1 -0
- package/dist/sdk/workflow-check-provider-H3CUOLUD.mjs +28 -0
- package/dist/sdk/workflow-check-provider-H3CUOLUD.mjs.map +1 -0
- package/dist/sdk/workflow-check-provider-YUNNF4KC.mjs +28 -0
- package/dist/sdk/workflow-check-provider-YUNNF4KC.mjs.map +1 -0
- package/dist/sdk/workflow-registry-KFWSDSLM.mjs +12 -0
- package/dist/sdk/workflow-registry-KFWSDSLM.mjs.map +1 -0
- package/dist/slack/socket-runner.d.ts +2 -0
- package/dist/slack/socket-runner.d.ts.map +1 -1
- package/dist/state-machine/context/workflow-inputs.d.ts +20 -0
- package/dist/state-machine/context/workflow-inputs.d.ts.map +1 -0
- package/dist/state-machine/dispatch/execution-invoker.d.ts.map +1 -1
- package/dist/state-machine/dispatch/foreach-processor.d.ts.map +1 -1
- package/dist/state-machine/dispatch/stats-manager.d.ts.map +1 -1
- package/dist/state-machine/states/level-dispatch.d.ts.map +1 -1
- package/dist/state-machine/states/routing.d.ts +2 -1
- package/dist/state-machine/states/routing.d.ts.map +1 -1
- package/dist/traces/{run-2026-01-28T16-15-24-569Z.ndjson → run-2026-01-31T16-37-22-321Z.ndjson} +84 -84
- package/dist/traces/{run-2026-01-28T16-16-09-757Z.ndjson → run-2026-01-31T16-38-06-031Z.ndjson} +1013 -1013
- package/dist/types/config.d.ts +3 -1
- package/dist/types/config.d.ts.map +1 -1
- package/dist/utils/human-id.d.ts +12 -0
- package/dist/utils/human-id.d.ts.map +1 -0
- package/dist/utils/worktree-manager.d.ts +3 -0
- package/dist/utils/worktree-manager.d.ts.map +1 -1
- package/dist/workflow-executor.d.ts.map +1 -1
- package/dist/workflow-registry.d.ts +1 -0
- package/dist/workflow-registry.d.ts.map +1 -1
- package/package.json +2 -2
- package/dist/sdk/chunk-BHZ4CKUS.mjs.map +0 -1
- package/dist/sdk/chunk-PVITVJ6J.mjs.map +0 -1
- package/dist/sdk/chunk-YLQ4UN62.mjs.map +0 -1
- package/dist/sdk/github-frontend-6Q4BISZX.mjs.map +0 -1
- /package/dist/sdk/{check-provider-registry-AQ3JETBG.mjs.map → check-provider-registry-3KI5RKXT.mjs.map} +0 -0
- /package/dist/sdk/{config-RQQPMLRD.mjs.map → check-provider-registry-IYILYY35.mjs.map} +0 -0
- /package/dist/sdk/{routing-DEY2AIXM.mjs.map → config-5AUYQFHE.mjs.map} +0 -0
- /package/dist/sdk/{host-P5NQICP7.mjs.map → host-4MT3EW2I.mjs.map} +0 -0
package/dist/docs/fail-if.md
CHANGED
|
@@ -24,25 +24,109 @@ fail_if: outputs["fetch-tickets"].error
|
|
|
24
24
|
|
|
25
25
|
Inside the expression you can use:
|
|
26
26
|
|
|
27
|
+
### Primary context variables
|
|
28
|
+
|
|
27
29
|
- `output`: the current check's structured output.
|
|
28
30
|
- Includes `issues` and any other fields produced by the provider.
|
|
29
|
-
- For custom schemas, all top
|
|
31
|
+
- For custom schemas, all top-level JSON fields are preserved and exposed here.
|
|
30
32
|
- For command output that is JSON, fields are available directly; for plain text, treat `output` as a string.
|
|
31
33
|
- `outputs`: a map of dependency outputs keyed by check name. Each value is that check's `output` if present; otherwise the whole check result.
|
|
32
34
|
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
-
|
|
36
|
-
-
|
|
37
|
-
-
|
|
35
|
+
### Additional context variables
|
|
36
|
+
|
|
37
|
+
- `memory`: accessor for the memory store (see [Memory](./memory.md))
|
|
38
|
+
- `memory.get(key, namespace?)` - Get a value
|
|
39
|
+
- `memory.has(key, namespace?)` - Check if key exists
|
|
40
|
+
- `memory.list(namespace?)` - List keys
|
|
41
|
+
- `memory.getAll(namespace?)` - Get all key-value pairs
|
|
42
|
+
- `inputs`: workflow inputs (for workflows)
|
|
43
|
+
- `env`: environment variables
|
|
44
|
+
- `debug`: debug information (if available)
|
|
45
|
+
- `debug.errors` - Array of error messages
|
|
46
|
+
- `debug.processingTime` - Processing time in milliseconds
|
|
47
|
+
- `debug.provider` - AI provider used
|
|
48
|
+
- `debug.model` - AI model used
|
|
49
|
+
|
|
50
|
+
### Context for `if` conditions
|
|
51
|
+
|
|
52
|
+
When used in `if` conditions (not `fail_if`), additional context is available:
|
|
53
|
+
|
|
54
|
+
- `branch`: current branch name
|
|
55
|
+
- `baseBranch`: target branch (default: `main`)
|
|
56
|
+
- `filesChanged`: array of changed file paths
|
|
57
|
+
- `filesCount`: number of changed files
|
|
58
|
+
- `event`: GitHub event context with `event_name`, `action`, `repository`, etc.
|
|
59
|
+
- `checkName`, `schema`, `group`: check metadata
|
|
60
|
+
|
|
61
|
+
### Legacy context (backward compatibility)
|
|
62
|
+
|
|
63
|
+
- `issues`: shorthand for `output.issues`
|
|
64
|
+
- `criticalIssues`, `errorIssues`, `warningIssues`, `infoIssues`, `totalIssues`: count of issues by severity
|
|
65
|
+
- `metadata`: object containing `checkName`, `schema`, `group`, issue counts, `hasChanges`, `branch`, `event`
|
|
66
|
+
|
|
67
|
+
## Helper functions
|
|
68
|
+
|
|
69
|
+
### String helpers
|
|
70
|
+
- `contains(haystack, needle)` - Case-insensitive substring check
|
|
71
|
+
- `startsWith(s, prefix)` - Case-insensitive prefix check
|
|
72
|
+
- `endsWith(s, suffix)` - Case-insensitive suffix check
|
|
73
|
+
- `length(x)` - Length of string, array, or object keys
|
|
74
|
+
|
|
75
|
+
### Control helpers
|
|
76
|
+
- `always()` - Always returns `true`
|
|
77
|
+
- `success()` - Returns `true`
|
|
78
|
+
- `failure()` - Returns `false`
|
|
79
|
+
|
|
80
|
+
### Debugging
|
|
81
|
+
- `log(...args)` - Print debug output prefixed with emoji. See [Debugging Guide](./debugging.md)
|
|
82
|
+
|
|
83
|
+
### Issue/file matching helpers
|
|
84
|
+
- `hasIssue(issues, field, value)` - Check if any issue has a field matching value
|
|
85
|
+
- `countIssues(issues, field, value)` - Count issues matching field/value
|
|
86
|
+
- `hasFileMatching(issues, pattern)` - Check if any issue affects a file matching pattern
|
|
87
|
+
- `hasIssueWith(issues, field, value)` - Alias for `hasIssue`
|
|
88
|
+
- `hasFileWith(issues, pattern)` - Alias for `hasFileMatching`
|
|
89
|
+
|
|
90
|
+
### Author permission helpers
|
|
91
|
+
- `hasMinPermission(level)` - Check if author has at least the specified permission level
|
|
92
|
+
- `isOwner()` - Check if author is repository owner
|
|
93
|
+
- `isMember()` - Check if author is organization member
|
|
94
|
+
- `isCollaborator()` - Check if author is collaborator
|
|
95
|
+
- `isContributor()` - Check if author has contributed before
|
|
96
|
+
- `isFirstTimer()` - Check if author is a first-time contributor
|
|
97
|
+
|
|
98
|
+
See [Author Permissions](./author-permissions.md) for detailed usage.
|
|
38
99
|
|
|
39
|
-
Truthiness
|
|
100
|
+
## Truthiness
|
|
101
|
+
|
|
102
|
+
Truthiness rules follow JavaScript: non-empty strings are truthy, `""` and `null`/`undefined` are falsy, `0` is falsy.
|
|
103
|
+
|
|
104
|
+
## Complex failure conditions
|
|
105
|
+
|
|
106
|
+
For more control, use the complex form with additional options:
|
|
107
|
+
|
|
108
|
+
```yaml
|
|
109
|
+
failure_conditions:
|
|
110
|
+
no_critical_issues:
|
|
111
|
+
condition: "criticalIssues > 0"
|
|
112
|
+
message: "Critical security issues found"
|
|
113
|
+
severity: error # error, warning, or info
|
|
114
|
+
halt_execution: true # Stop all execution immediately
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
Options:
|
|
118
|
+
- `condition`: The expression to evaluate (required)
|
|
119
|
+
- `message`: Human-readable message when condition triggers (optional)
|
|
120
|
+
- `severity`: Issue severity level - `error`, `warning`, or `info` (default: `error`)
|
|
121
|
+
- `halt_execution`: If `true`, stops all workflow execution immediately (default: `false`)
|
|
40
122
|
|
|
41
123
|
## What happens when a condition is met
|
|
42
124
|
|
|
43
|
-
- The engine adds an
|
|
125
|
+
- The engine adds an issue to the check with ruleId `<checkName>_fail_if` (or `global_fail_if` for the global rule).
|
|
126
|
+
- Issue severity is `error` by default (configurable with complex form).
|
|
44
127
|
- Direct dependents of that check are skipped with reason `dependency_failed`.
|
|
45
|
-
- Skipped checks do not execute their providers; they appear as
|
|
128
|
+
- Skipped checks do not execute their providers; they appear as skipped in the details table.
|
|
129
|
+
- If `halt_execution: true`, the entire workflow stops immediately.
|
|
46
130
|
|
|
47
131
|
Only direct dependencies gate execution. Transitive checks are gated through the chain (i.e., if A fails B, and C depends on B, C will also be skipped once B is skipped).
|
|
48
132
|
|
|
@@ -88,8 +172,29 @@ fail_if: output.some(x => x.status === 'fail')
|
|
|
88
172
|
|
|
89
173
|
Per‑item fail logic is not evaluated via `fail_if`; use `if:` to skip item work or emit issues inside the per‑item action.
|
|
90
174
|
|
|
175
|
+
## Multi-line expressions
|
|
176
|
+
|
|
177
|
+
You can write multi-line expressions with debug statements:
|
|
178
|
+
|
|
179
|
+
```yaml
|
|
180
|
+
fail_if: |
|
|
181
|
+
log("Checking output:", output);
|
|
182
|
+
log("Issue count:", output.issues?.length);
|
|
183
|
+
output.issues?.some(i => i.severity === 'critical')
|
|
184
|
+
```
|
|
185
|
+
|
|
186
|
+
The last expression determines the boolean result. Lines are joined using the comma operator.
|
|
187
|
+
|
|
91
188
|
## Notes
|
|
92
189
|
|
|
93
|
-
- Fail conditions are evaluated during dependency
|
|
94
|
-
- Issue ruleIds are consistent: `<checkName>_fail_if` for per
|
|
190
|
+
- Fail conditions are evaluated during dependency-aware execution as part of the engine (not only in providers), ensuring dependents are reliably skipped even if a provider path didn't attach issues.
|
|
191
|
+
- Issue ruleIds are consistent: `<checkName>_fail_if` for per-check and `global_fail_if` for global.
|
|
192
|
+
- Expressions support optional chaining (`?.`) and nullish coalescing (`??`) for safe property access.
|
|
193
|
+
- If expression evaluation fails, the condition is treated as `false` (fail-safe behavior).
|
|
194
|
+
|
|
195
|
+
## Related documentation
|
|
95
196
|
|
|
197
|
+
- [Author Permissions](./author-permissions.md) - Permission helper functions
|
|
198
|
+
- [Debugging Guide](./debugging.md) - Using `log()` and other debugging techniques
|
|
199
|
+
- [Memory](./memory.md) - Memory store access in expressions
|
|
200
|
+
- [Configuration](./configuration.md) - Full configuration reference
|
|
@@ -1,5 +1,17 @@
|
|
|
1
1
|
# Enhanced Failure Condition System for Visor
|
|
2
2
|
|
|
3
|
+
> **Status: Partially Outdated**
|
|
4
|
+
>
|
|
5
|
+
> This document was written during initial implementation and some details are now outdated.
|
|
6
|
+
> For current usage, see:
|
|
7
|
+
> - [fail-if.md](./fail-if.md) - Primary documentation for failure conditions (recommended)
|
|
8
|
+
> - [failure-conditions-schema.md](./failure-conditions-schema.md) - Configuration schema reference
|
|
9
|
+
>
|
|
10
|
+
> Key differences from current implementation:
|
|
11
|
+
> - Integration is now via `StateMachineExecutionEngine` (not `CheckExecutionEngine`)
|
|
12
|
+
> - The simpler `fail_if` syntax is now the recommended approach
|
|
13
|
+
> - Additional helper functions exist (see fail-if.md for complete list)
|
|
14
|
+
|
|
3
15
|
This document provides a complete overview of the enhanced failure condition configuration system implemented for the Visor code review tool.
|
|
4
16
|
|
|
5
17
|
## Overview
|
|
@@ -18,9 +30,9 @@ The enhanced failure condition system allows users to define flexible, powerful
|
|
|
18
30
|
- TypeScript interfaces for failure conditions
|
|
19
31
|
- Context object definition for expression evaluation
|
|
20
32
|
|
|
21
|
-
3. **
|
|
22
|
-
- Integration with
|
|
23
|
-
- Automated evaluation after check completion
|
|
33
|
+
3. **StateMachineExecutionEngine Integration** (`src/state-machine-execution-engine.ts`)
|
|
34
|
+
- Integration with the state machine execution pipeline
|
|
35
|
+
- Automated evaluation after check completion via `evaluateFailureConditions()` method
|
|
24
36
|
|
|
25
37
|
## Configuration Schema
|
|
26
38
|
|
|
@@ -85,11 +97,20 @@ The context object available to all JavaScript expressions (evaluated in a secur
|
|
|
85
97
|
|
|
86
98
|
## Available Helper Functions
|
|
87
99
|
|
|
100
|
+
> **Note**: This list is incomplete. See [fail-if.md](./fail-if.md#helper-functions) for the complete and current list of helper functions.
|
|
101
|
+
|
|
88
102
|
### Issue Analysis
|
|
89
103
|
- `hasIssueWith(issues, field, value)` - Check if any issue has field matching value
|
|
90
104
|
- `countIssues(issues, field, value)` - Count issues with field matching value
|
|
91
105
|
- `hasFileWith(issues, text)` - Check if any issue file path contains text
|
|
92
106
|
|
|
107
|
+
### Additional helpers (not listed here)
|
|
108
|
+
- String helpers: `contains()`, `startsWith()`, `endsWith()`, `length()`
|
|
109
|
+
- Control helpers: `always()`, `success()`, `failure()`
|
|
110
|
+
- Debug helper: `log()` for debugging expressions
|
|
111
|
+
- Permission helpers: `hasMinPermission()`, `isOwner()`, `isMember()`, etc.
|
|
112
|
+
- Memory accessor: `memory.get()`, `memory.has()`, `memory.list()`, `memory.getAll()`
|
|
113
|
+
|
|
93
114
|
## Example Use Cases
|
|
94
115
|
|
|
95
116
|
### Basic Quality Gates
|
|
@@ -157,13 +178,15 @@ failure_conditions:
|
|
|
157
178
|
|
|
158
179
|
## Integration Points
|
|
159
180
|
|
|
160
|
-
###
|
|
181
|
+
### StateMachineExecutionEngine
|
|
161
182
|
```typescript
|
|
162
183
|
// Evaluate conditions after check completion
|
|
163
184
|
const results = await engine.evaluateFailureConditions(
|
|
164
185
|
checkName,
|
|
165
186
|
reviewSummary,
|
|
166
|
-
config
|
|
187
|
+
config,
|
|
188
|
+
previousOutputs,
|
|
189
|
+
authorAssociation
|
|
167
190
|
);
|
|
168
191
|
|
|
169
192
|
// Check if execution should halt
|
|
@@ -172,6 +195,8 @@ if (FailureConditionEvaluator.shouldHaltExecution(results)) {
|
|
|
172
195
|
}
|
|
173
196
|
```
|
|
174
197
|
|
|
198
|
+
> **Note**: The integration was originally in `CheckExecutionEngine` but has been migrated to `StateMachineExecutionEngine` as part of the engine refactor.
|
|
199
|
+
|
|
175
200
|
### GitHub Action Integration
|
|
176
201
|
Failure conditions can be used to:
|
|
177
202
|
- Set action exit codes
|
|
@@ -268,4 +293,13 @@ steps:
|
|
|
268
293
|
|
|
269
294
|
The enhanced failure condition system provides a flexible, powerful foundation for implementing custom quality gates and policies in Visor. By leveraging JavaScript expressions (evaluated in a secure sandbox) with comprehensive context access, teams can create sophisticated review workflows that adapt to their specific needs and standards.
|
|
270
295
|
|
|
271
|
-
The system maintains full backward compatibility while opening new possibilities for automated code quality enforcement and intelligent review assistance.
|
|
296
|
+
The system maintains full backward compatibility while opening new possibilities for automated code quality enforcement and intelligent review assistance.
|
|
297
|
+
|
|
298
|
+
## Related Documentation
|
|
299
|
+
|
|
300
|
+
- [fail-if.md](./fail-if.md) - **Primary documentation** for failure conditions (recommended starting point)
|
|
301
|
+
- [failure-conditions-schema.md](./failure-conditions-schema.md) - Configuration schema reference
|
|
302
|
+
- [author-permissions.md](./author-permissions.md) - Permission helper functions
|
|
303
|
+
- [debugging.md](./debugging.md) - Using `log()` and debugging techniques
|
|
304
|
+
- [memory.md](./memory.md) - Memory store access in expressions
|
|
305
|
+
- [configuration.md](./configuration.md) - Full configuration reference
|
|
@@ -1,42 +1,63 @@
|
|
|
1
|
-
#
|
|
1
|
+
# Failure Condition Configuration Schema
|
|
2
2
|
|
|
3
|
-
This document describes the
|
|
3
|
+
This document describes the failure condition configuration system for Visor that supports JavaScript expressions (evaluated in a secure sandbox) for flexible and powerful failure evaluation.
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
> **Note:** The simple `fail_if` syntax is now preferred over the legacy `failure_conditions` object syntax. See [Fail If](./fail-if.md) for the recommended approach.
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
## Quick Start: Using `fail_if` (Recommended)
|
|
8
|
+
|
|
9
|
+
The simplest way to define failure conditions:
|
|
8
10
|
|
|
9
11
|
```yaml
|
|
10
12
|
version: "1.0"
|
|
11
13
|
|
|
12
|
-
# Global
|
|
13
|
-
|
|
14
|
-
# Simple JavaScript expression for basic failure conditions
|
|
15
|
-
critical_threshold: "metadata.criticalIssues > 0"
|
|
14
|
+
# Global fail_if applies to all steps unless overridden
|
|
15
|
+
fail_if: "output.error || criticalIssues > 0"
|
|
16
16
|
|
|
17
|
-
|
|
18
|
-
|
|
17
|
+
steps:
|
|
18
|
+
security:
|
|
19
|
+
type: ai
|
|
20
|
+
prompt: "Analyze for security vulnerabilities..."
|
|
21
|
+
schema: code-review
|
|
22
|
+
on:
|
|
23
|
+
- pr_opened
|
|
24
|
+
- pr_updated
|
|
25
|
+
# Step-specific fail_if overrides global
|
|
26
|
+
fail_if: "criticalIssues > 0 || errorIssues >= 3"
|
|
19
27
|
|
|
20
|
-
|
|
21
|
-
|
|
28
|
+
performance:
|
|
29
|
+
type: ai
|
|
30
|
+
prompt: "Analyze performance implications..."
|
|
31
|
+
schema: code-review
|
|
32
|
+
on:
|
|
33
|
+
- pr_opened
|
|
34
|
+
- pr_updated
|
|
35
|
+
# Complex condition with helper functions
|
|
36
|
+
fail_if: "hasIssue(issues, 'category', 'performance') && errorIssues > 1"
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
## Legacy: Complex Failure Conditions
|
|
22
40
|
|
|
23
|
-
|
|
24
|
-
deployment_blocker: "metadata.criticalIssues > 0 || (metadata.errorIssues > 5 && metadata.checkName == 'security')"
|
|
41
|
+
For more control, use the complex `failure_conditions` object syntax (deprecated but still supported):
|
|
25
42
|
|
|
26
|
-
|
|
43
|
+
```yaml
|
|
44
|
+
version: "1.0"
|
|
45
|
+
|
|
46
|
+
# Object syntax for complex conditions with additional options
|
|
27
47
|
failure_conditions:
|
|
28
48
|
critical_security_issues:
|
|
29
|
-
condition: "
|
|
49
|
+
condition: "criticalIssues > 0"
|
|
30
50
|
message: "Critical security issues detected - deployment blocked"
|
|
31
51
|
severity: "error"
|
|
52
|
+
halt_execution: true # Stop all execution immediately
|
|
32
53
|
|
|
33
54
|
performance_degradation:
|
|
34
|
-
condition: "
|
|
55
|
+
condition: "hasIssue(issues, 'category', 'performance') && errorIssues >= 3"
|
|
35
56
|
message: "Performance issues detected that may impact production"
|
|
36
57
|
severity: "warning"
|
|
37
58
|
|
|
38
59
|
insufficient_coverage:
|
|
39
|
-
condition: "
|
|
60
|
+
condition: "totalIssues > 15"
|
|
40
61
|
message: "Too many code quality issues - consider additional review"
|
|
41
62
|
severity: "info"
|
|
42
63
|
|
|
@@ -49,69 +70,160 @@ steps:
|
|
|
49
70
|
on:
|
|
50
71
|
- pr_opened
|
|
51
72
|
- pr_updated
|
|
52
|
-
|
|
53
|
-
# Check-specific failure conditions override global ones
|
|
54
|
-
failure_conditions:
|
|
55
|
-
block_on_any_critical: "metadata.criticalIssues > 0"
|
|
56
|
-
warn_on_multiple_errors: "metadata.errorIssues >= 2"
|
|
57
|
-
|
|
58
|
-
performance:
|
|
59
|
-
type: ai
|
|
60
|
-
prompt: "Analyze performance implications..."
|
|
61
|
-
group: review
|
|
62
|
-
schema: code-review
|
|
63
|
-
on:
|
|
64
|
-
- pr_opened
|
|
65
|
-
- pr_updated
|
|
66
|
-
|
|
67
|
-
# Inherits global failure conditions unless overridden
|
|
73
|
+
# Step-specific failure conditions override global ones with same name
|
|
68
74
|
failure_conditions:
|
|
69
|
-
|
|
75
|
+
block_on_any_critical: "criticalIssues > 0"
|
|
76
|
+
warn_on_multiple_errors: "errorIssues >= 2"
|
|
70
77
|
```
|
|
71
78
|
|
|
72
79
|
### Advanced JavaScript Expression Examples
|
|
73
80
|
|
|
74
81
|
```yaml
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
82
|
+
steps:
|
|
83
|
+
security-check:
|
|
84
|
+
type: ai
|
|
85
|
+
prompt: "Analyze for security issues..."
|
|
86
|
+
# Issue analysis with helper functions
|
|
87
|
+
fail_if: "hasFileWith(issues, 'sql') && hasIssue(issues, 'severity', 'critical')"
|
|
78
88
|
|
|
79
|
-
|
|
80
|
-
|
|
89
|
+
critical-files:
|
|
90
|
+
type: ai
|
|
91
|
+
prompt: "Review critical files..."
|
|
92
|
+
# Multiple file types analysis
|
|
93
|
+
fail_if: "(hasFileWith(issues, '.ts') || hasFileWith(issues, '.js')) && hasIssue(issues, 'severity', 'critical')"
|
|
81
94
|
|
|
82
|
-
|
|
83
|
-
|
|
95
|
+
performance-check:
|
|
96
|
+
type: ai
|
|
97
|
+
prompt: "Analyze performance..."
|
|
98
|
+
# Time-based conditions (if debug info is available)
|
|
99
|
+
fail_if: "debug && debug.processingTime > 60000 && errorIssues > 0"
|
|
84
100
|
|
|
85
|
-
|
|
86
|
-
|
|
101
|
+
auth-check:
|
|
102
|
+
type: ai
|
|
103
|
+
prompt: "Check authentication code..."
|
|
104
|
+
# File-specific security checks with counting
|
|
105
|
+
fail_if: "hasFileWith(issues, 'auth') && countIssues(issues, 'severity', 'critical') > 0"
|
|
87
106
|
|
|
88
|
-
|
|
89
|
-
|
|
107
|
+
security-count:
|
|
108
|
+
type: ai
|
|
109
|
+
prompt: "Security analysis..."
|
|
110
|
+
# Count-based conditions
|
|
111
|
+
fail_if: "countIssues(issues, 'category', 'security') >= 3"
|
|
112
|
+
```
|
|
90
113
|
|
|
91
|
-
|
|
92
|
-
|
|
114
|
+
## Available Context Variables
|
|
115
|
+
|
|
116
|
+
### Primary Context
|
|
117
|
+
|
|
118
|
+
| Variable | Description |
|
|
119
|
+
|----------|-------------|
|
|
120
|
+
| `output` | Current step's structured output (includes `issues` and provider-specific fields) |
|
|
121
|
+
| `outputs` | Map of dependency outputs keyed by step name |
|
|
122
|
+
| `memory` | Memory store accessor (see [Memory](./memory.md)) |
|
|
123
|
+
| `inputs` | Workflow inputs (for workflows) |
|
|
124
|
+
| `env` | Environment variables |
|
|
125
|
+
| `debug` | Debug information (`errors`, `processingTime`, `provider`, `model`) |
|
|
126
|
+
|
|
127
|
+
### Legacy Context (Backward Compatibility)
|
|
128
|
+
|
|
129
|
+
| Variable | Description |
|
|
130
|
+
|----------|-------------|
|
|
131
|
+
| `issues` | Shorthand for `output.issues` |
|
|
132
|
+
| `criticalIssues` | Count of critical severity issues |
|
|
133
|
+
| `errorIssues` | Count of error severity issues |
|
|
134
|
+
| `warningIssues` | Count of warning severity issues |
|
|
135
|
+
| `infoIssues` | Count of info severity issues |
|
|
136
|
+
| `totalIssues` | Total issue count |
|
|
137
|
+
| `metadata` | Object with `checkName`, `schema`, `group`, issue counts, etc. |
|
|
138
|
+
|
|
139
|
+
### Additional Context for `if` Conditions
|
|
140
|
+
|
|
141
|
+
| Variable | Description |
|
|
142
|
+
|----------|-------------|
|
|
143
|
+
| `branch` | Current branch name |
|
|
144
|
+
| `baseBranch` | Target branch (default: `main`) |
|
|
145
|
+
| `filesChanged` | Array of changed file paths |
|
|
146
|
+
| `filesCount` | Number of changed files |
|
|
147
|
+
| `event` | GitHub event context (`event_name`, `action`, `repository`, etc.) |
|
|
148
|
+
| `checkName` | Current check name |
|
|
149
|
+
| `schema` | Check schema |
|
|
150
|
+
| `group` | Check group |
|
|
151
|
+
|
|
152
|
+
## Available Helper Functions
|
|
153
|
+
|
|
154
|
+
### String Helpers
|
|
155
|
+
|
|
156
|
+
| Function | Description |
|
|
157
|
+
|----------|-------------|
|
|
158
|
+
| `contains(haystack, needle)` | Case-insensitive substring check |
|
|
159
|
+
| `startsWith(s, prefix)` | Case-insensitive prefix check |
|
|
160
|
+
| `endsWith(s, suffix)` | Case-insensitive suffix check |
|
|
161
|
+
| `length(x)` | Length of string, array, or object keys |
|
|
162
|
+
|
|
163
|
+
### Control Helpers
|
|
164
|
+
|
|
165
|
+
| Function | Description |
|
|
166
|
+
|----------|-------------|
|
|
167
|
+
| `always()` | Always returns `true` |
|
|
168
|
+
| `success()` | Returns `true` |
|
|
169
|
+
| `failure()` | Returns `false` |
|
|
170
|
+
|
|
171
|
+
### Issue/File Matching Helpers
|
|
172
|
+
|
|
173
|
+
| Function | Description |
|
|
174
|
+
|----------|-------------|
|
|
175
|
+
| `hasIssue(issues, field, value)` | Check if any issue has a field matching value |
|
|
176
|
+
| `countIssues(issues, field, value)` | Count issues matching field/value |
|
|
177
|
+
| `hasFileMatching(issues, pattern)` | Check if any issue affects a file matching pattern |
|
|
178
|
+
| `hasIssueWith(issues, field, value)` | Alias for `hasIssue` |
|
|
179
|
+
| `hasFileWith(issues, pattern)` | Alias for `hasFileMatching` |
|
|
180
|
+
|
|
181
|
+
### Permission Helpers
|
|
182
|
+
|
|
183
|
+
| Function | Description |
|
|
184
|
+
|----------|-------------|
|
|
185
|
+
| `hasMinPermission(level)` | Check if author has at least the specified permission level |
|
|
186
|
+
| `isOwner()` | Check if author is repository owner |
|
|
187
|
+
| `isMember()` | Check if author is organization member |
|
|
188
|
+
| `isCollaborator()` | Check if author is collaborator |
|
|
189
|
+
| `isContributor()` | Check if author has contributed before |
|
|
190
|
+
| `isFirstTimer()` | Check if author is a first-time contributor |
|
|
191
|
+
|
|
192
|
+
### Debugging
|
|
193
|
+
|
|
194
|
+
| Function | Description |
|
|
195
|
+
|----------|-------------|
|
|
196
|
+
| `log(...args)` | Print debug output prefixed with emoji (see [Debugging Guide](./debugging.md)) |
|
|
93
197
|
|
|
94
|
-
|
|
95
|
-
multiple_security_issues: "countIssues(issues, 'category', 'security') >= 3"
|
|
198
|
+
## Configuration Priority and Inheritance
|
|
96
199
|
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
200
|
+
1. **Step-specific conditions** override global conditions with the same name
|
|
201
|
+
2. **Global conditions** apply to all steps unless specifically overridden
|
|
202
|
+
3. **Multiple conditions** are evaluated independently - any true condition triggers a failure
|
|
100
203
|
|
|
101
|
-
##
|
|
204
|
+
## Interaction with Criticality
|
|
205
|
+
|
|
206
|
+
Failure conditions (`fail_if`) and design-by-contract (`assume`, `guarantee`) work together with criticality:
|
|
207
|
+
|
|
208
|
+
- **Critical steps** (external/control-plane/policy):
|
|
209
|
+
- Require meaningful `assume` and `guarantee`.
|
|
210
|
+
- `continue_on_failure: false` by default; dependents skip when this step fails.
|
|
211
|
+
- Retries only for transient provider faults; no auto-retry for logical failures (`fail_if`/`guarantee`).
|
|
212
|
+
- **Non-critical steps**:
|
|
213
|
+
- Contracts recommended; may allow `continue_on_failure: true`.
|
|
214
|
+
- Same retry bounds; tolerant gating.
|
|
102
215
|
|
|
103
|
-
|
|
104
|
-
2. **Global conditions** apply to all checks unless specifically overridden
|
|
105
|
-
3. **Built-in conditions** (if any) have the lowest priority
|
|
106
|
-
4. **Multiple conditions** are evaluated independently - any true condition triggers a failure
|
|
216
|
+
See [Fault Management and Contracts](./guides/fault-management-and-contracts.md) for the full policy checklist and examples.
|
|
107
217
|
|
|
108
218
|
## Backward Compatibility
|
|
109
219
|
|
|
110
|
-
The
|
|
220
|
+
The system maintains full backward compatibility with both `fail_if` and `failure_conditions`:
|
|
111
221
|
|
|
112
222
|
```yaml
|
|
113
|
-
#
|
|
223
|
+
# Simple fail_if (recommended)
|
|
114
224
|
version: "1.0"
|
|
225
|
+
fail_if: "criticalIssues > 0"
|
|
226
|
+
|
|
115
227
|
steps:
|
|
116
228
|
security:
|
|
117
229
|
type: ai
|
|
@@ -119,11 +231,15 @@ steps:
|
|
|
119
231
|
on:
|
|
120
232
|
- pr_opened
|
|
121
233
|
- pr_updated
|
|
234
|
+
fail_if: "errorIssues >= 1"
|
|
122
235
|
|
|
123
|
-
#
|
|
236
|
+
# Legacy failure_conditions (still supported)
|
|
124
237
|
version: "1.0"
|
|
125
238
|
failure_conditions:
|
|
126
|
-
default_critical:
|
|
239
|
+
default_critical:
|
|
240
|
+
condition: "criticalIssues > 0"
|
|
241
|
+
message: "Critical issues found"
|
|
242
|
+
severity: error
|
|
127
243
|
|
|
128
244
|
steps:
|
|
129
245
|
security:
|
|
@@ -132,42 +248,82 @@ steps:
|
|
|
132
248
|
on:
|
|
133
249
|
- pr_opened
|
|
134
250
|
- pr_updated
|
|
251
|
+
failure_conditions:
|
|
252
|
+
security_specific: "errorIssues >= 1"
|
|
253
|
+
```
|
|
135
254
|
|
|
136
|
-
##
|
|
255
|
+
## Migration Guide
|
|
137
256
|
|
|
138
|
-
|
|
257
|
+
### Migrating from `failure_conditions` to `fail_if`
|
|
139
258
|
|
|
140
|
-
|
|
141
|
-
- Require meaningful `assume` and `guarantee`.
|
|
142
|
-
- `continue_on_failure: false` by default; dependents skip when this step fails.
|
|
143
|
-
- Retries only for transient provider faults; no auto‑retry for logical failures (`fail_if`/`guarantee`).
|
|
144
|
-
- Non‑critical steps:
|
|
145
|
-
- Contracts recommended; may allow `continue_on_failure: true`.
|
|
146
|
-
- Same retry bounds; tolerant gating.
|
|
259
|
+
If you have existing `failure_conditions` configurations, migrate them to `fail_if`:
|
|
147
260
|
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
261
|
+
**Before (legacy):**
|
|
262
|
+
```yaml
|
|
263
|
+
failure_conditions:
|
|
264
|
+
critical_blocker:
|
|
265
|
+
condition: "metadata.criticalIssues > 0"
|
|
266
|
+
message: "Critical issues found"
|
|
267
|
+
severity: error
|
|
268
|
+
quality_gate:
|
|
269
|
+
condition: "metadata.totalIssues > 10"
|
|
270
|
+
severity: warning
|
|
151
271
|
```
|
|
152
272
|
|
|
153
|
-
|
|
273
|
+
**After (recommended):**
|
|
274
|
+
```yaml
|
|
275
|
+
# Simple condition - just use fail_if
|
|
276
|
+
fail_if: "criticalIssues > 0 || totalIssues > 10"
|
|
277
|
+
```
|
|
154
278
|
|
|
155
|
-
|
|
279
|
+
If you need the `halt_execution` feature, keep using the complex form:
|
|
156
280
|
```yaml
|
|
157
|
-
# Add to existing configuration
|
|
158
281
|
failure_conditions:
|
|
159
|
-
critical_blocker:
|
|
160
|
-
|
|
282
|
+
critical_blocker:
|
|
283
|
+
condition: "criticalIssues > 0"
|
|
284
|
+
message: "Critical issues found"
|
|
285
|
+
severity: error
|
|
286
|
+
halt_execution: true
|
|
287
|
+
```
|
|
288
|
+
|
|
289
|
+
### Step-by-Step Migration
|
|
290
|
+
|
|
291
|
+
1. Replace `metadata.criticalIssues` with `criticalIssues` (legacy variables still work)
|
|
292
|
+
2. Replace `hasIssueWith` with `hasIssue` (both work, but `hasIssue` is clearer)
|
|
293
|
+
3. Use `fail_if` string instead of `failure_conditions` object when possible
|
|
294
|
+
4. Test with `--debug` flag to verify expressions evaluate correctly
|
|
295
|
+
|
|
296
|
+
### Testing Your Conditions
|
|
297
|
+
|
|
298
|
+
Use debug mode to test conditions and refine expressions:
|
|
299
|
+
|
|
300
|
+
```bash
|
|
301
|
+
visor --config your-config.yaml --debug
|
|
161
302
|
```
|
|
162
303
|
|
|
163
|
-
|
|
304
|
+
You can also use the `log()` helper in expressions:
|
|
164
305
|
```yaml
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
security_gate: "metadata.errorIssues >= 1"
|
|
306
|
+
fail_if: |
|
|
307
|
+
log("Issues:", issues);
|
|
308
|
+
log("Critical count:", criticalIssues);
|
|
309
|
+
criticalIssues > 0
|
|
170
310
|
```
|
|
171
311
|
|
|
172
|
-
|
|
173
|
-
|
|
312
|
+
## Complex Failure Condition Options
|
|
313
|
+
|
|
314
|
+
When using the object syntax, these options are available:
|
|
315
|
+
|
|
316
|
+
| Option | Type | Default | Description |
|
|
317
|
+
|--------|------|---------|-------------|
|
|
318
|
+
| `condition` | string | required | JavaScript expression to evaluate |
|
|
319
|
+
| `message` | string | - | Human-readable message when condition triggers |
|
|
320
|
+
| `severity` | string | `"error"` | Severity level: `error`, `warning`, or `info` |
|
|
321
|
+
| `halt_execution` | boolean | `false` | If `true`, stops all workflow execution immediately |
|
|
322
|
+
|
|
323
|
+
## Related Documentation
|
|
324
|
+
|
|
325
|
+
- [Fail If](./fail-if.md) - Recommended simple syntax for failure conditions
|
|
326
|
+
- [Author Permissions](./author-permissions.md) - Permission helper functions
|
|
327
|
+
- [Debugging Guide](./debugging.md) - Using `log()` and debugging techniques
|
|
328
|
+
- [Memory](./memory.md) - Memory store access in expressions
|
|
329
|
+
- [Fault Management and Contracts](./guides/fault-management-and-contracts.md) - Criticality and contracts
|