autonomous-coding-toolkit 1.0.0
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/.claude-plugin/marketplace.json +22 -0
- package/.claude-plugin/plugin.json +13 -0
- package/LICENSE +21 -0
- package/Makefile +21 -0
- package/README.md +140 -0
- package/SECURITY.md +28 -0
- package/agents/bash-expert.md +113 -0
- package/agents/dependency-auditor.md +138 -0
- package/agents/integration-tester.md +120 -0
- package/agents/lesson-scanner.md +149 -0
- package/agents/python-expert.md +179 -0
- package/agents/service-monitor.md +141 -0
- package/agents/shell-expert.md +147 -0
- package/benchmarks/runner.sh +147 -0
- package/benchmarks/tasks/01-rest-endpoint/rubric.sh +29 -0
- package/benchmarks/tasks/01-rest-endpoint/task.md +17 -0
- package/benchmarks/tasks/02-refactor-module/task.md +8 -0
- package/benchmarks/tasks/03-fix-integration-bug/task.md +8 -0
- package/benchmarks/tasks/04-add-test-coverage/task.md +8 -0
- package/benchmarks/tasks/05-multi-file-feature/task.md +8 -0
- package/bin/act.js +238 -0
- package/commands/autocode.md +6 -0
- package/commands/cancel-ralph.md +18 -0
- package/commands/code-factory.md +53 -0
- package/commands/create-prd.md +55 -0
- package/commands/ralph-loop.md +18 -0
- package/commands/run-plan.md +117 -0
- package/commands/submit-lesson.md +122 -0
- package/docs/ARCHITECTURE.md +630 -0
- package/docs/CONTRIBUTING.md +125 -0
- package/docs/lessons/0001-bare-exception-swallowing.md +34 -0
- package/docs/lessons/0002-async-def-without-await.md +28 -0
- package/docs/lessons/0003-create-task-without-callback.md +28 -0
- package/docs/lessons/0004-hardcoded-test-counts.md +28 -0
- package/docs/lessons/0005-sqlite-without-closing.md +33 -0
- package/docs/lessons/0006-venv-pip-path.md +27 -0
- package/docs/lessons/0007-runner-state-self-rejection.md +35 -0
- package/docs/lessons/0008-quality-gate-blind-spot.md +33 -0
- package/docs/lessons/0009-parser-overcount-empty-batches.md +36 -0
- package/docs/lessons/0010-local-outside-function-bash.md +33 -0
- package/docs/lessons/0011-batch-tests-for-unimplemented-code.md +36 -0
- package/docs/lessons/0012-api-markdown-unescaped-chars.md +33 -0
- package/docs/lessons/0013-export-prefix-env-parsing.md +33 -0
- package/docs/lessons/0014-decorator-registry-import-side-effect.md +43 -0
- package/docs/lessons/0015-frontend-backend-schema-drift.md +43 -0
- package/docs/lessons/0016-event-driven-cold-start-seeding.md +44 -0
- package/docs/lessons/0017-copy-paste-logic-diverges.md +43 -0
- package/docs/lessons/0018-layer-passes-pipeline-broken.md +45 -0
- package/docs/lessons/0019-systemd-envfile-ignores-export.md +41 -0
- package/docs/lessons/0020-persist-state-incrementally.md +44 -0
- package/docs/lessons/0021-dual-axis-testing.md +48 -0
- package/docs/lessons/0022-jsx-factory-shadowing.md +43 -0
- package/docs/lessons/0023-static-analysis-spiral.md +51 -0
- package/docs/lessons/0024-shared-pipeline-implementation.md +55 -0
- package/docs/lessons/0025-defense-in-depth-all-entry-points.md +65 -0
- package/docs/lessons/0026-linter-no-rules-false-enforcement.md +54 -0
- package/docs/lessons/0027-jsx-silent-prop-drop.md +64 -0
- package/docs/lessons/0028-no-infrastructure-in-client-code.md +49 -0
- package/docs/lessons/0029-never-write-secrets-to-files.md +61 -0
- package/docs/lessons/0030-cache-merge-not-replace.md +62 -0
- package/docs/lessons/0031-verify-units-at-boundaries.md +66 -0
- package/docs/lessons/0032-module-lifecycle-subscribe-unsubscribe.md +89 -0
- package/docs/lessons/0033-async-iteration-mutable-snapshot.md +72 -0
- package/docs/lessons/0034-caller-missing-await-silent-discard.md +65 -0
- package/docs/lessons/0035-duplicate-registration-silent-overwrite.md +85 -0
- package/docs/lessons/0036-websocket-dirty-disconnect.md +33 -0
- package/docs/lessons/0037-parallel-agents-worktree-corruption.md +31 -0
- package/docs/lessons/0038-subscribe-no-stored-ref.md +36 -0
- package/docs/lessons/0039-fallback-or-default-hides-bugs.md +34 -0
- package/docs/lessons/0040-event-firehose-filter-first.md +36 -0
- package/docs/lessons/0041-ambiguous-base-dir-path-nesting.md +32 -0
- package/docs/lessons/0042-spec-compliance-insufficient.md +36 -0
- package/docs/lessons/0043-exact-count-extensible-collections.md +32 -0
- package/docs/lessons/0044-relative-file-deps-worktree.md +39 -0
- package/docs/lessons/0045-iterative-design-improvement.md +33 -0
- package/docs/lessons/0046-plan-assertion-math-bugs.md +38 -0
- package/docs/lessons/0047-pytest-single-threaded-default.md +37 -0
- package/docs/lessons/0048-integration-wiring-batch.md +40 -0
- package/docs/lessons/0049-ab-verification.md +41 -0
- package/docs/lessons/0050-editing-sourced-files-during-execution.md +33 -0
- package/docs/lessons/0051-infrastructure-fixes-cant-self-heal.md +30 -0
- package/docs/lessons/0052-uncommitted-changes-poison-quality-gates.md +31 -0
- package/docs/lessons/0053-jq-compact-flag-inconsistency.md +31 -0
- package/docs/lessons/0054-parser-matches-inside-code-blocks.md +30 -0
- package/docs/lessons/0055-agents-compensate-for-garbled-prompts.md +31 -0
- package/docs/lessons/0056-grep-count-exit-code-on-zero.md +42 -0
- package/docs/lessons/0057-new-artifacts-break-git-clean-gates.md +42 -0
- package/docs/lessons/0058-dead-config-keys-never-consumed.md +49 -0
- package/docs/lessons/0059-contract-test-shared-structures.md +53 -0
- package/docs/lessons/0060-set-e-silent-death-in-runners.md +53 -0
- package/docs/lessons/0061-context-injection-dirty-state.md +50 -0
- package/docs/lessons/0062-sibling-bug-neighborhood-scan.md +29 -0
- package/docs/lessons/0063-one-flag-two-lifetimes.md +31 -0
- package/docs/lessons/0064-test-passes-wrong-reason.md +31 -0
- package/docs/lessons/0065-pipefail-grep-count-double-output.md +39 -0
- package/docs/lessons/0066-local-keyword-outside-function.md +37 -0
- package/docs/lessons/0067-stdin-hang-non-interactive-shell.md +36 -0
- package/docs/lessons/0068-agent-builds-wrong-thing-correctly.md +31 -0
- package/docs/lessons/0069-plan-quality-dominates-execution.md +30 -0
- package/docs/lessons/0070-spec-echo-back-prevents-drift.md +31 -0
- package/docs/lessons/0071-positive-instructions-outperform-negative.md +30 -0
- package/docs/lessons/0072-lost-in-the-middle-context-placement.md +30 -0
- package/docs/lessons/0073-unscoped-lessons-cause-false-positives.md +30 -0
- package/docs/lessons/0074-stale-context-injection-wrong-batch.md +32 -0
- package/docs/lessons/0075-research-artifacts-must-persist.md +32 -0
- package/docs/lessons/0076-wrong-decomposition-contaminates-downstream.md +30 -0
- package/docs/lessons/0077-cherry-pick-merges-need-manual-resolution.md +30 -0
- package/docs/lessons/0078-static-review-without-live-test.md +30 -0
- package/docs/lessons/0079-integration-wiring-batch-required.md +32 -0
- package/docs/lessons/FRAMEWORK.md +161 -0
- package/docs/lessons/SUMMARY.md +201 -0
- package/docs/lessons/TEMPLATE.md +85 -0
- package/docs/plans/2026-02-21-code-factory-v2-design.md +204 -0
- package/docs/plans/2026-02-21-code-factory-v2-implementation-plan.md +2189 -0
- package/docs/plans/2026-02-21-code-factory-v2-phase4-design.md +537 -0
- package/docs/plans/2026-02-21-code-factory-v2-phase4-implementation-plan.md +2012 -0
- package/docs/plans/2026-02-21-hardening-pass-design.md +108 -0
- package/docs/plans/2026-02-21-hardening-pass-plan.md +1378 -0
- package/docs/plans/2026-02-21-mab-research-report.md +406 -0
- package/docs/plans/2026-02-21-marketplace-restructure-design.md +240 -0
- package/docs/plans/2026-02-21-marketplace-restructure-plan.md +832 -0
- package/docs/plans/2026-02-21-phase4-completion-plan.md +697 -0
- package/docs/plans/2026-02-21-validator-suite-design.md +148 -0
- package/docs/plans/2026-02-21-validator-suite-plan.md +540 -0
- package/docs/plans/2026-02-22-mab-research-round2.md +556 -0
- package/docs/plans/2026-02-22-mab-run-design.md +462 -0
- package/docs/plans/2026-02-22-mab-run-plan.md +2046 -0
- package/docs/plans/2026-02-22-operations-design-methodology-research.md +681 -0
- package/docs/plans/2026-02-22-research-agent-failure-taxonomy.md +532 -0
- package/docs/plans/2026-02-22-research-code-guideline-policies.md +886 -0
- package/docs/plans/2026-02-22-research-codebase-audit-refactoring.md +908 -0
- package/docs/plans/2026-02-22-research-coding-standards-documentation.md +541 -0
- package/docs/plans/2026-02-22-research-competitive-landscape.md +687 -0
- package/docs/plans/2026-02-22-research-comprehensive-testing.md +1076 -0
- package/docs/plans/2026-02-22-research-context-utilization.md +459 -0
- package/docs/plans/2026-02-22-research-cost-quality-tradeoff.md +548 -0
- package/docs/plans/2026-02-22-research-lesson-transferability.md +508 -0
- package/docs/plans/2026-02-22-research-multi-agent-coordination.md +312 -0
- package/docs/plans/2026-02-22-research-phase-integration.md +602 -0
- package/docs/plans/2026-02-22-research-plan-quality.md +428 -0
- package/docs/plans/2026-02-22-research-prompt-engineering.md +558 -0
- package/docs/plans/2026-02-22-research-unconventional-perspectives.md +528 -0
- package/docs/plans/2026-02-22-research-user-adoption.md +638 -0
- package/docs/plans/2026-02-22-research-verification-effectiveness.md +433 -0
- package/docs/plans/2026-02-23-agent-suite-design.md +299 -0
- package/docs/plans/2026-02-23-agent-suite-plan.md +578 -0
- package/docs/plans/2026-02-23-phase3-cost-infrastructure-design.md +148 -0
- package/docs/plans/2026-02-23-phase3-cost-infrastructure-plan.md +1062 -0
- package/docs/plans/2026-02-23-research-bash-expert-agent.md +543 -0
- package/docs/plans/2026-02-23-research-dependency-auditor-agent.md +564 -0
- package/docs/plans/2026-02-23-research-improving-existing-agents.md +503 -0
- package/docs/plans/2026-02-23-research-integration-tester-agent.md +454 -0
- package/docs/plans/2026-02-23-research-python-expert-agent.md +429 -0
- package/docs/plans/2026-02-23-research-service-monitor-agent.md +425 -0
- package/docs/plans/2026-02-23-research-shell-expert-agent.md +533 -0
- package/docs/plans/2026-02-23-roadmap-to-completion.md +530 -0
- package/docs/plans/2026-02-24-headless-module-split-design.md +98 -0
- package/docs/plans/2026-02-24-headless-module-split.md +443 -0
- package/docs/plans/2026-02-24-lesson-scope-metadata-design.md +228 -0
- package/docs/plans/2026-02-24-lesson-scope-metadata-plan.md +968 -0
- package/docs/plans/2026-02-24-npm-packaging-design.md +841 -0
- package/docs/plans/2026-02-24-npm-packaging-plan.md +1965 -0
- package/docs/plans/audit-findings.md +186 -0
- package/docs/telegram-notification-format.md +98 -0
- package/examples/example-plan.md +51 -0
- package/examples/example-prd.json +72 -0
- package/examples/example-roadmap.md +33 -0
- package/examples/quickstart-plan.md +63 -0
- package/hooks/hooks.json +26 -0
- package/hooks/setup-symlinks.sh +48 -0
- package/hooks/stop-hook.sh +135 -0
- package/package.json +47 -0
- package/policies/bash.md +71 -0
- package/policies/python.md +71 -0
- package/policies/testing.md +61 -0
- package/policies/universal.md +60 -0
- package/scripts/analyze-report.sh +97 -0
- package/scripts/architecture-map.sh +145 -0
- package/scripts/auto-compound.sh +273 -0
- package/scripts/batch-audit.sh +42 -0
- package/scripts/batch-test.sh +101 -0
- package/scripts/entropy-audit.sh +221 -0
- package/scripts/failure-digest.sh +51 -0
- package/scripts/generate-ast-rules.sh +96 -0
- package/scripts/init.sh +112 -0
- package/scripts/lesson-check.sh +428 -0
- package/scripts/lib/common.sh +61 -0
- package/scripts/lib/cost-tracking.sh +153 -0
- package/scripts/lib/ollama.sh +60 -0
- package/scripts/lib/progress-writer.sh +128 -0
- package/scripts/lib/run-plan-context.sh +215 -0
- package/scripts/lib/run-plan-echo-back.sh +231 -0
- package/scripts/lib/run-plan-headless.sh +396 -0
- package/scripts/lib/run-plan-notify.sh +57 -0
- package/scripts/lib/run-plan-parser.sh +81 -0
- package/scripts/lib/run-plan-prompt.sh +215 -0
- package/scripts/lib/run-plan-quality-gate.sh +132 -0
- package/scripts/lib/run-plan-routing.sh +315 -0
- package/scripts/lib/run-plan-sampling.sh +170 -0
- package/scripts/lib/run-plan-scoring.sh +146 -0
- package/scripts/lib/run-plan-state.sh +142 -0
- package/scripts/lib/run-plan-team.sh +199 -0
- package/scripts/lib/telegram.sh +54 -0
- package/scripts/lib/thompson-sampling.sh +176 -0
- package/scripts/license-check.sh +74 -0
- package/scripts/mab-run.sh +575 -0
- package/scripts/module-size-check.sh +146 -0
- package/scripts/patterns/async-no-await.yml +5 -0
- package/scripts/patterns/bare-except.yml +6 -0
- package/scripts/patterns/empty-catch.yml +6 -0
- package/scripts/patterns/hardcoded-localhost.yml +9 -0
- package/scripts/patterns/retry-loop-no-backoff.yml +12 -0
- package/scripts/pipeline-status.sh +197 -0
- package/scripts/policy-check.sh +226 -0
- package/scripts/prior-art-search.sh +133 -0
- package/scripts/promote-mab-lessons.sh +126 -0
- package/scripts/prompts/agent-a-superpowers.md +29 -0
- package/scripts/prompts/agent-b-ralph.md +29 -0
- package/scripts/prompts/judge-agent.md +61 -0
- package/scripts/prompts/planner-agent.md +44 -0
- package/scripts/pull-community-lessons.sh +90 -0
- package/scripts/quality-gate.sh +266 -0
- package/scripts/research-gate.sh +90 -0
- package/scripts/run-plan.sh +329 -0
- package/scripts/scope-infer.sh +159 -0
- package/scripts/setup-ralph-loop.sh +155 -0
- package/scripts/telemetry.sh +230 -0
- package/scripts/tests/run-all-tests.sh +52 -0
- package/scripts/tests/test-act-cli.sh +46 -0
- package/scripts/tests/test-agents-md.sh +87 -0
- package/scripts/tests/test-analyze-report.sh +114 -0
- package/scripts/tests/test-architecture-map.sh +89 -0
- package/scripts/tests/test-auto-compound.sh +169 -0
- package/scripts/tests/test-batch-test.sh +65 -0
- package/scripts/tests/test-benchmark-runner.sh +25 -0
- package/scripts/tests/test-common.sh +168 -0
- package/scripts/tests/test-cost-tracking.sh +158 -0
- package/scripts/tests/test-echo-back.sh +180 -0
- package/scripts/tests/test-entropy-audit.sh +146 -0
- package/scripts/tests/test-failure-digest.sh +66 -0
- package/scripts/tests/test-generate-ast-rules.sh +145 -0
- package/scripts/tests/test-helpers.sh +82 -0
- package/scripts/tests/test-init.sh +47 -0
- package/scripts/tests/test-lesson-check.sh +278 -0
- package/scripts/tests/test-lesson-local.sh +55 -0
- package/scripts/tests/test-license-check.sh +109 -0
- package/scripts/tests/test-mab-run.sh +182 -0
- package/scripts/tests/test-ollama-lib.sh +49 -0
- package/scripts/tests/test-ollama.sh +60 -0
- package/scripts/tests/test-pipeline-status.sh +198 -0
- package/scripts/tests/test-policy-check.sh +124 -0
- package/scripts/tests/test-prior-art-search.sh +96 -0
- package/scripts/tests/test-progress-writer.sh +140 -0
- package/scripts/tests/test-promote-mab-lessons.sh +110 -0
- package/scripts/tests/test-pull-community-lessons.sh +149 -0
- package/scripts/tests/test-quality-gate.sh +241 -0
- package/scripts/tests/test-research-gate.sh +132 -0
- package/scripts/tests/test-run-plan-cli.sh +86 -0
- package/scripts/tests/test-run-plan-context.sh +305 -0
- package/scripts/tests/test-run-plan-e2e.sh +153 -0
- package/scripts/tests/test-run-plan-headless.sh +424 -0
- package/scripts/tests/test-run-plan-notify.sh +124 -0
- package/scripts/tests/test-run-plan-parser.sh +217 -0
- package/scripts/tests/test-run-plan-prompt.sh +254 -0
- package/scripts/tests/test-run-plan-quality-gate.sh +222 -0
- package/scripts/tests/test-run-plan-routing.sh +178 -0
- package/scripts/tests/test-run-plan-scoring.sh +148 -0
- package/scripts/tests/test-run-plan-state.sh +261 -0
- package/scripts/tests/test-run-plan-team.sh +157 -0
- package/scripts/tests/test-scope-infer.sh +150 -0
- package/scripts/tests/test-setup-ralph-loop.sh +63 -0
- package/scripts/tests/test-telegram-env.sh +38 -0
- package/scripts/tests/test-telegram.sh +121 -0
- package/scripts/tests/test-telemetry.sh +46 -0
- package/scripts/tests/test-thompson-sampling.sh +139 -0
- package/scripts/tests/test-validate-all.sh +60 -0
- package/scripts/tests/test-validate-commands.sh +89 -0
- package/scripts/tests/test-validate-hooks.sh +98 -0
- package/scripts/tests/test-validate-lessons.sh +150 -0
- package/scripts/tests/test-validate-plan-quality.sh +235 -0
- package/scripts/tests/test-validate-plans.sh +187 -0
- package/scripts/tests/test-validate-plugin.sh +106 -0
- package/scripts/tests/test-validate-prd.sh +184 -0
- package/scripts/tests/test-validate-skills.sh +134 -0
- package/scripts/validate-all.sh +57 -0
- package/scripts/validate-commands.sh +67 -0
- package/scripts/validate-hooks.sh +89 -0
- package/scripts/validate-lessons.sh +98 -0
- package/scripts/validate-plan-quality.sh +369 -0
- package/scripts/validate-plans.sh +120 -0
- package/scripts/validate-plugin.sh +86 -0
- package/scripts/validate-policies.sh +42 -0
- package/scripts/validate-prd.sh +118 -0
- package/scripts/validate-skills.sh +96 -0
- package/skills/autocode/SKILL.md +285 -0
- package/skills/autocode/ab-verification.md +51 -0
- package/skills/autocode/code-quality-standards.md +37 -0
- package/skills/autocode/competitive-mode.md +364 -0
- package/skills/brainstorming/SKILL.md +97 -0
- package/skills/capture-lesson/SKILL.md +187 -0
- package/skills/check-lessons/SKILL.md +116 -0
- package/skills/dispatching-parallel-agents/SKILL.md +110 -0
- package/skills/executing-plans/SKILL.md +85 -0
- package/skills/finishing-a-development-branch/SKILL.md +201 -0
- package/skills/receiving-code-review/SKILL.md +72 -0
- package/skills/requesting-code-review/SKILL.md +59 -0
- package/skills/requesting-code-review/code-reviewer.md +82 -0
- package/skills/research/SKILL.md +145 -0
- package/skills/roadmap/SKILL.md +115 -0
- package/skills/subagent-driven-development/SKILL.md +98 -0
- package/skills/subagent-driven-development/code-quality-reviewer-prompt.md +18 -0
- package/skills/subagent-driven-development/implementer-prompt.md +73 -0
- package/skills/subagent-driven-development/spec-reviewer-prompt.md +57 -0
- package/skills/systematic-debugging/SKILL.md +134 -0
- package/skills/systematic-debugging/condition-based-waiting.md +64 -0
- package/skills/systematic-debugging/defense-in-depth.md +32 -0
- package/skills/systematic-debugging/root-cause-tracing.md +55 -0
- package/skills/test-driven-development/SKILL.md +167 -0
- package/skills/using-git-worktrees/SKILL.md +219 -0
- package/skills/using-superpowers/SKILL.md +54 -0
- package/skills/verification-before-completion/SKILL.md +140 -0
- package/skills/verify/SKILL.md +82 -0
- package/skills/writing-plans/SKILL.md +128 -0
- package/skills/writing-skills/SKILL.md +93 -0
|
@@ -0,0 +1,241 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
# Test quality-gate.sh — verifies refactored behavior using common.sh
|
|
3
|
+
set -euo pipefail
|
|
4
|
+
|
|
5
|
+
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
6
|
+
QG="$SCRIPT_DIR/../quality-gate.sh"
|
|
7
|
+
|
|
8
|
+
FAILURES=0
|
|
9
|
+
TESTS=0
|
|
10
|
+
|
|
11
|
+
assert_eq() {
|
|
12
|
+
local desc="$1" expected="$2" actual="$3"
|
|
13
|
+
TESTS=$((TESTS + 1))
|
|
14
|
+
if [[ "$expected" != "$actual" ]]; then
|
|
15
|
+
echo "FAIL: $desc"
|
|
16
|
+
echo " expected: $expected"
|
|
17
|
+
echo " actual: $actual"
|
|
18
|
+
FAILURES=$((FAILURES + 1))
|
|
19
|
+
else
|
|
20
|
+
echo "PASS: $desc"
|
|
21
|
+
fi
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
assert_exit() {
|
|
25
|
+
local desc="$1" expected_exit="$2"
|
|
26
|
+
shift 2
|
|
27
|
+
local actual_exit=0
|
|
28
|
+
"$@" >/dev/null 2>&1 || actual_exit=$?
|
|
29
|
+
TESTS=$((TESTS + 1))
|
|
30
|
+
if [[ "$expected_exit" != "$actual_exit" ]]; then
|
|
31
|
+
echo "FAIL: $desc"
|
|
32
|
+
echo " expected exit: $expected_exit"
|
|
33
|
+
echo " actual exit: $actual_exit"
|
|
34
|
+
FAILURES=$((FAILURES + 1))
|
|
35
|
+
else
|
|
36
|
+
echo "PASS: $desc"
|
|
37
|
+
fi
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
assert_contains() {
|
|
41
|
+
local desc="$1" needle="$2" haystack="$3"
|
|
42
|
+
TESTS=$((TESTS + 1))
|
|
43
|
+
if echo "$haystack" | grep -qF "$needle"; then
|
|
44
|
+
echo "PASS: $desc"
|
|
45
|
+
else
|
|
46
|
+
echo "FAIL: $desc"
|
|
47
|
+
echo " expected to contain: $needle"
|
|
48
|
+
echo " in: $(echo "$haystack" | head -5)"
|
|
49
|
+
FAILURES=$((FAILURES + 1))
|
|
50
|
+
fi
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
WORK=$(mktemp -d)
|
|
54
|
+
trap 'rm -rf "$WORK"' EXIT
|
|
55
|
+
|
|
56
|
+
# === CLI tests ===
|
|
57
|
+
|
|
58
|
+
assert_exit "no args exits 1" 1 bash "$QG"
|
|
59
|
+
assert_exit "--help exits 0" 0 bash "$QG" --help
|
|
60
|
+
assert_exit "nonexistent dir exits 1" 1 bash "$QG" --project-root /nonexistent/path
|
|
61
|
+
|
|
62
|
+
# === Sources common.sh ===
|
|
63
|
+
|
|
64
|
+
# Check that the script sources common.sh (grep for the source line)
|
|
65
|
+
TESTS=$((TESTS + 1))
|
|
66
|
+
if grep -q 'source.*lib/common.sh' "$QG"; then
|
|
67
|
+
echo "PASS: quality-gate.sh sources lib/common.sh"
|
|
68
|
+
else
|
|
69
|
+
echo "FAIL: quality-gate.sh sources lib/common.sh"
|
|
70
|
+
echo " expected: source line for lib/common.sh"
|
|
71
|
+
FAILURES=$((FAILURES + 1))
|
|
72
|
+
fi
|
|
73
|
+
|
|
74
|
+
# === Python project detection via detect_project_type ===
|
|
75
|
+
|
|
76
|
+
# Create a minimal Python project with no actual test suite
|
|
77
|
+
# (so the test suite step will run but fail — we just care about detection)
|
|
78
|
+
mkdir -p "$WORK/py-proj"
|
|
79
|
+
touch "$WORK/py-proj/pyproject.toml"
|
|
80
|
+
# Create a fake .venv/bin/python that exits 0
|
|
81
|
+
mkdir -p "$WORK/py-proj/.venv/bin"
|
|
82
|
+
cat > "$WORK/py-proj/.venv/bin/python" <<'FAKE'
|
|
83
|
+
#!/bin/bash
|
|
84
|
+
echo "1 passed"
|
|
85
|
+
exit 0
|
|
86
|
+
FAKE
|
|
87
|
+
chmod +x "$WORK/py-proj/.venv/bin/python"
|
|
88
|
+
|
|
89
|
+
# Run quality-gate on the python project — lesson-check will be skipped (no git)
|
|
90
|
+
output=$(bash "$QG" --project-root "$WORK/py-proj" 2>&1) || true
|
|
91
|
+
assert_contains "detects pytest project" "Detected: pytest project" "$output"
|
|
92
|
+
|
|
93
|
+
# === Node project detection ===
|
|
94
|
+
|
|
95
|
+
mkdir -p "$WORK/node-proj"
|
|
96
|
+
echo '{"name":"test","scripts":{"test":"echo ok"}}' > "$WORK/node-proj/package.json"
|
|
97
|
+
output=$(bash "$QG" --project-root "$WORK/node-proj" 2>&1) || true
|
|
98
|
+
assert_contains "detects npm project" "Detected: npm project" "$output"
|
|
99
|
+
|
|
100
|
+
# === Lint check output (Python project with ruff) ===
|
|
101
|
+
|
|
102
|
+
output=$(bash "$QG" --project-root "$WORK/py-proj" 2>&1) || true
|
|
103
|
+
assert_contains "lint check section present" "Lint Check" "$output"
|
|
104
|
+
|
|
105
|
+
# === Lint check output (Node project — no eslint config → skipped) ===
|
|
106
|
+
|
|
107
|
+
output=$(bash "$QG" --project-root "$WORK/node-proj" 2>&1) || true
|
|
108
|
+
assert_contains "node lint skipped without config" "No eslint config found" "$output"
|
|
109
|
+
|
|
110
|
+
# === --quick flag skips lint ===
|
|
111
|
+
|
|
112
|
+
output=$(bash "$QG" --project-root "$WORK/py-proj" --quick 2>&1) || true
|
|
113
|
+
TESTS=$((TESTS + 1))
|
|
114
|
+
if echo "$output" | grep -qF "Lint Check"; then
|
|
115
|
+
echo "FAIL: --quick skips lint check"
|
|
116
|
+
echo " Lint Check header should not appear with --quick"
|
|
117
|
+
FAILURES=$((FAILURES + 1))
|
|
118
|
+
else
|
|
119
|
+
echo "PASS: --quick skips lint check"
|
|
120
|
+
fi
|
|
121
|
+
assert_contains "--quick still runs tests" "Test Suite" "$output"
|
|
122
|
+
assert_contains "--quick still runs memory" "Memory Check" "$output"
|
|
123
|
+
|
|
124
|
+
# === --with-license flag adds license check ===
|
|
125
|
+
|
|
126
|
+
output=$(bash "$QG" --project-root "$WORK/py-proj" --with-license 2>&1) || true
|
|
127
|
+
assert_contains "--with-license runs license check" "License Check" "$output"
|
|
128
|
+
|
|
129
|
+
# === without --with-license, no license check ===
|
|
130
|
+
|
|
131
|
+
output=$(bash "$QG" --project-root "$WORK/py-proj" 2>&1) || true
|
|
132
|
+
TESTS=$((TESTS + 1))
|
|
133
|
+
# License Check should NOT appear in the quality-gate section headers
|
|
134
|
+
# (it may appear in lesson check output, so check for the specific gate header)
|
|
135
|
+
if echo "$output" | grep -qF "Quality Gate: License Check"; then
|
|
136
|
+
echo "FAIL: no license check without --with-license"
|
|
137
|
+
FAILURES=$((FAILURES + 1))
|
|
138
|
+
else
|
|
139
|
+
echo "PASS: no license check without --with-license"
|
|
140
|
+
fi
|
|
141
|
+
|
|
142
|
+
# === --quick and --with-license combined ===
|
|
143
|
+
|
|
144
|
+
output=$(bash "$QG" --project-root "$WORK/py-proj" --quick --with-license 2>&1) || true
|
|
145
|
+
TESTS=$((TESTS + 1))
|
|
146
|
+
if echo "$output" | grep -qF "Lint Check"; then
|
|
147
|
+
echo "FAIL: --quick --with-license skips lint"
|
|
148
|
+
FAILURES=$((FAILURES + 1))
|
|
149
|
+
else
|
|
150
|
+
echo "PASS: --quick --with-license skips lint"
|
|
151
|
+
fi
|
|
152
|
+
assert_contains "--quick --with-license keeps license" "License Check" "$output"
|
|
153
|
+
|
|
154
|
+
# === Memory check output ===
|
|
155
|
+
|
|
156
|
+
output=$(bash "$QG" --project-root "$WORK/py-proj" 2>&1) || true
|
|
157
|
+
# Should contain either "Memory OK" or "WARNING: Low memory" or "skipped"
|
|
158
|
+
TESTS=$((TESTS + 1))
|
|
159
|
+
if echo "$output" | grep -qE "(Memory OK|WARNING.*memory|WARNING.*Consider|Memory check skipped)"; then
|
|
160
|
+
echo "PASS: memory check runs"
|
|
161
|
+
else
|
|
162
|
+
echo "FAIL: memory check runs"
|
|
163
|
+
echo " expected memory check output"
|
|
164
|
+
echo " got: $output"
|
|
165
|
+
FAILURES=$((FAILURES + 1))
|
|
166
|
+
fi
|
|
167
|
+
|
|
168
|
+
# Memory display should use decimal GB (e.g., "3.9G") not truncated integer
|
|
169
|
+
TESTS=$((TESTS + 1))
|
|
170
|
+
if echo "$output" | grep -qE 'Memory OK \([0-9]+\.[0-9]+G'; then
|
|
171
|
+
echo "PASS: memory display uses decimal GB (MB-based, not truncated)"
|
|
172
|
+
else
|
|
173
|
+
# On systems where free is unavailable, this is expected to skip
|
|
174
|
+
if echo "$output" | grep -qF "Memory check skipped"; then
|
|
175
|
+
echo "PASS: memory display skipped (free unavailable — acceptable)"
|
|
176
|
+
else
|
|
177
|
+
echo "FAIL: memory display should show decimal GB (e.g., 3.9G)"
|
|
178
|
+
echo " got: $(echo "$output" | grep -i memory)"
|
|
179
|
+
FAILURES=$((FAILURES + 1))
|
|
180
|
+
fi
|
|
181
|
+
fi
|
|
182
|
+
|
|
183
|
+
# quality-gate.sh should not use free -g (only free -m via common.sh)
|
|
184
|
+
TESTS=$((TESTS + 1))
|
|
185
|
+
if grep -q 'free -g' "$QG"; then
|
|
186
|
+
echo "FAIL: quality-gate.sh should not use free -g (use free -m)"
|
|
187
|
+
FAILURES=$((FAILURES + 1))
|
|
188
|
+
else
|
|
189
|
+
echo "PASS: quality-gate.sh does not use free -g"
|
|
190
|
+
fi
|
|
191
|
+
|
|
192
|
+
# === Word-splitting fix (#5): changed_files passed to lesson-check via array ===
|
|
193
|
+
|
|
194
|
+
TESTS=$((TESTS + 1))
|
|
195
|
+
# Should use readarray and "${changed_array[@]}" — not bare $changed_files
|
|
196
|
+
if grep -q 'readarray.*changed_array' "$QG" && grep -q '"${changed_array\[@\]}"' "$QG"; then
|
|
197
|
+
echo "PASS: quality-gate passes files to lesson-check via array (no word-splitting, bug #5)"
|
|
198
|
+
else
|
|
199
|
+
echo "FAIL: quality-gate should use readarray + \${changed_array[@]} for lesson-check args (bug #5)"
|
|
200
|
+
FAILURES=$((FAILURES + 1))
|
|
201
|
+
fi
|
|
202
|
+
|
|
203
|
+
# The old unquoted $changed_files pattern must not be present
|
|
204
|
+
TESTS=$((TESTS + 1))
|
|
205
|
+
# Strip comment lines and look for the old unquoted expansion used as args
|
|
206
|
+
if grep -v '^\s*#' "$QG" | grep -q 'lesson-check.sh \$changed_files\b'; then
|
|
207
|
+
echo "FAIL: quality-gate still passes unquoted \$changed_files to lesson-check (bug #5)"
|
|
208
|
+
FAILURES=$((FAILURES + 1))
|
|
209
|
+
else
|
|
210
|
+
echo "PASS: quality-gate does not pass unquoted \$changed_files to lesson-check"
|
|
211
|
+
fi
|
|
212
|
+
|
|
213
|
+
# === ast-grep section present in full mode (advisory, doesn't fail gate) ===
|
|
214
|
+
|
|
215
|
+
output=$(bash "$QG" --project-root "$WORK/py-proj" 2>&1) || true
|
|
216
|
+
TESTS=$((TESTS + 1))
|
|
217
|
+
if echo "$output" | grep -qiE "structural|ast-grep"; then
|
|
218
|
+
echo "PASS: ast-grep section present in full mode"
|
|
219
|
+
else
|
|
220
|
+
echo "FAIL: ast-grep section should be present in full mode"
|
|
221
|
+
FAILURES=$((FAILURES + 1))
|
|
222
|
+
fi
|
|
223
|
+
|
|
224
|
+
# ast-grep section should be skipped in --quick mode
|
|
225
|
+
output=$(bash "$QG" --project-root "$WORK/py-proj" --quick 2>&1) || true
|
|
226
|
+
TESTS=$((TESTS + 1))
|
|
227
|
+
if echo "$output" | grep -qF "Structural Analysis"; then
|
|
228
|
+
echo "FAIL: --quick should skip ast-grep structural analysis"
|
|
229
|
+
FAILURES=$((FAILURES + 1))
|
|
230
|
+
else
|
|
231
|
+
echo "PASS: --quick skips ast-grep structural analysis"
|
|
232
|
+
fi
|
|
233
|
+
|
|
234
|
+
# === Summary ===
|
|
235
|
+
echo ""
|
|
236
|
+
echo "Results: $((TESTS - FAILURES))/$TESTS passed"
|
|
237
|
+
if [[ $FAILURES -gt 0 ]]; then
|
|
238
|
+
echo "FAILURES: $FAILURES"
|
|
239
|
+
exit 1
|
|
240
|
+
fi
|
|
241
|
+
echo "ALL PASSED"
|
|
@@ -0,0 +1,132 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
# Tests for research-gate.sh
|
|
3
|
+
|
|
4
|
+
set -euo pipefail
|
|
5
|
+
|
|
6
|
+
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
7
|
+
GATE="$SCRIPT_DIR/../research-gate.sh"
|
|
8
|
+
PASS=0 FAIL=0 TOTAL=0
|
|
9
|
+
|
|
10
|
+
assert() {
|
|
11
|
+
local desc="$1" expected="$2" actual="$3"
|
|
12
|
+
TOTAL=$((TOTAL + 1))
|
|
13
|
+
if [[ "$expected" == "$actual" ]]; then
|
|
14
|
+
echo "PASS: $desc"
|
|
15
|
+
PASS=$((PASS + 1))
|
|
16
|
+
else
|
|
17
|
+
echo "FAIL: $desc (expected=$expected, actual=$actual)"
|
|
18
|
+
FAIL=$((FAIL + 1))
|
|
19
|
+
fi
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
tmpdir=$(mktemp -d)
|
|
23
|
+
trap 'rm -rf "$tmpdir"' EXIT
|
|
24
|
+
|
|
25
|
+
# Test 1: No blocking issues → exit 0
|
|
26
|
+
cat > "$tmpdir/clear.json" <<'EOF'
|
|
27
|
+
{
|
|
28
|
+
"feature": "test-feature",
|
|
29
|
+
"blocking_issues": [],
|
|
30
|
+
"warnings": [],
|
|
31
|
+
"confidence_ratings": {"approach": "high"}
|
|
32
|
+
}
|
|
33
|
+
EOF
|
|
34
|
+
output=$("$GATE" "$tmpdir/clear.json" 2>&1) || true
|
|
35
|
+
exit_code=$?
|
|
36
|
+
assert "no blockers: exit 0" "0" "$exit_code"
|
|
37
|
+
echo "$output" | grep -q "clear"
|
|
38
|
+
assert "no blockers: says clear" "0" "$?"
|
|
39
|
+
|
|
40
|
+
# Test 2: All resolved blocking issues → exit 0
|
|
41
|
+
cat > "$tmpdir/resolved.json" <<'EOF'
|
|
42
|
+
{
|
|
43
|
+
"feature": "test-feature",
|
|
44
|
+
"blocking_issues": [
|
|
45
|
+
{"issue": "missing dep", "resolved": true, "resolution": "installed"}
|
|
46
|
+
],
|
|
47
|
+
"warnings": []
|
|
48
|
+
}
|
|
49
|
+
EOF
|
|
50
|
+
exit_code=0
|
|
51
|
+
"$GATE" "$tmpdir/resolved.json" > /dev/null 2>&1 || exit_code=$?
|
|
52
|
+
assert "resolved blockers: exit 0" "0" "$exit_code"
|
|
53
|
+
|
|
54
|
+
# Test 3: Unresolved blocking issues → exit 1
|
|
55
|
+
cat > "$tmpdir/blocked.json" <<'EOF'
|
|
56
|
+
{
|
|
57
|
+
"feature": "test-feature",
|
|
58
|
+
"blocking_issues": [
|
|
59
|
+
{"issue": "no viable auth library", "resolved": false, "resolution": "evaluate alternatives"}
|
|
60
|
+
],
|
|
61
|
+
"warnings": []
|
|
62
|
+
}
|
|
63
|
+
EOF
|
|
64
|
+
exit_code=0
|
|
65
|
+
"$GATE" "$tmpdir/blocked.json" > /dev/null 2>&1 || exit_code=$?
|
|
66
|
+
assert "unresolved blockers: exit 1" "1" "$exit_code"
|
|
67
|
+
|
|
68
|
+
# Test 4: --force overrides blockers → exit 0
|
|
69
|
+
exit_code=0
|
|
70
|
+
output=$("$GATE" "$tmpdir/blocked.json" --force 2>&1) || exit_code=$?
|
|
71
|
+
assert "--force: exit 0" "0" "$exit_code"
|
|
72
|
+
assert "--force: shows warning" "1" "$(echo "$output" | grep -c "WARNING.*force")"
|
|
73
|
+
|
|
74
|
+
# Test 5: Missing file → exit 1
|
|
75
|
+
exit_code=0
|
|
76
|
+
"$GATE" "$tmpdir/nonexistent.json" > /dev/null 2>&1 || exit_code=$?
|
|
77
|
+
assert "missing file: exit 1" "1" "$exit_code"
|
|
78
|
+
|
|
79
|
+
# Test 6: Invalid JSON → exit 1
|
|
80
|
+
echo "not json" > "$tmpdir/invalid.json"
|
|
81
|
+
exit_code=0
|
|
82
|
+
"$GATE" "$tmpdir/invalid.json" > /dev/null 2>&1 || exit_code=$?
|
|
83
|
+
assert "invalid JSON: exit 1" "1" "$exit_code"
|
|
84
|
+
|
|
85
|
+
# Test 7: --help → exit 0
|
|
86
|
+
exit_code=0
|
|
87
|
+
output=$("$GATE" --help 2>&1) || exit_code=$?
|
|
88
|
+
assert "--help: exit 0" "0" "$exit_code"
|
|
89
|
+
assert "--help: shows usage" "1" "$(echo "$output" | grep -c "USAGE")"
|
|
90
|
+
|
|
91
|
+
# Test 8: Warnings present but no blockers → exit 0
|
|
92
|
+
cat > "$tmpdir/warnings.json" <<'EOF'
|
|
93
|
+
{
|
|
94
|
+
"feature": "test-feature",
|
|
95
|
+
"blocking_issues": [],
|
|
96
|
+
"warnings": ["deprecated API", "performance concern"]
|
|
97
|
+
}
|
|
98
|
+
EOF
|
|
99
|
+
exit_code=0
|
|
100
|
+
output=$("$GATE" "$tmpdir/warnings.json" 2>&1) || exit_code=$?
|
|
101
|
+
assert "warnings only: exit 0" "0" "$exit_code"
|
|
102
|
+
assert "warnings only: shows warning count" "1" "$(echo "$output" | grep -c "2 warning")"
|
|
103
|
+
|
|
104
|
+
# Test 9: No args → exit 1
|
|
105
|
+
exit_code=0
|
|
106
|
+
"$GATE" > /dev/null 2>&1 || exit_code=$?
|
|
107
|
+
assert "no args: exit 1" "1" "$exit_code"
|
|
108
|
+
|
|
109
|
+
# Test 10: Multiple unresolved + some resolved → exit 1
|
|
110
|
+
cat > "$tmpdir/mixed.json" <<'EOF'
|
|
111
|
+
{
|
|
112
|
+
"feature": "test-feature",
|
|
113
|
+
"blocking_issues": [
|
|
114
|
+
{"issue": "resolved one", "resolved": true},
|
|
115
|
+
{"issue": "still blocked", "resolved": false},
|
|
116
|
+
{"issue": "also blocked", "resolved": false}
|
|
117
|
+
],
|
|
118
|
+
"warnings": []
|
|
119
|
+
}
|
|
120
|
+
EOF
|
|
121
|
+
exit_code=0
|
|
122
|
+
output=$("$GATE" "$tmpdir/mixed.json" 2>&1) || exit_code=$?
|
|
123
|
+
assert "mixed blockers: exit 1" "1" "$exit_code"
|
|
124
|
+
assert "mixed blockers: shows count 2" "1" "$(echo "$output" | grep -c "2 unresolved")"
|
|
125
|
+
|
|
126
|
+
echo ""
|
|
127
|
+
echo "Results: $PASS/$TOTAL passed"
|
|
128
|
+
if [[ $FAIL -gt 0 ]]; then
|
|
129
|
+
echo "FAILURES: $FAIL"
|
|
130
|
+
exit 1
|
|
131
|
+
fi
|
|
132
|
+
echo "ALL PASSED"
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
# Test run-plan.sh CLI argument parsing and validation
|
|
3
|
+
set -euo pipefail
|
|
4
|
+
|
|
5
|
+
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
6
|
+
RUN_PLAN="$SCRIPT_DIR/../run-plan.sh"
|
|
7
|
+
|
|
8
|
+
FAILURES=0
|
|
9
|
+
TESTS=0
|
|
10
|
+
|
|
11
|
+
assert_exit() {
|
|
12
|
+
local desc="$1" expected_exit="$2"
|
|
13
|
+
shift 2
|
|
14
|
+
local actual_exit=0
|
|
15
|
+
local output
|
|
16
|
+
output=$("$@" 2>&1) || actual_exit=$?
|
|
17
|
+
TESTS=$((TESTS + 1))
|
|
18
|
+
if [[ "$actual_exit" -ne "$expected_exit" ]]; then
|
|
19
|
+
echo "FAIL: $desc"
|
|
20
|
+
echo " expected exit: $expected_exit"
|
|
21
|
+
echo " actual exit: $actual_exit"
|
|
22
|
+
echo " output: ${output:0:300}"
|
|
23
|
+
FAILURES=$((FAILURES + 1))
|
|
24
|
+
else
|
|
25
|
+
echo "PASS: $desc"
|
|
26
|
+
fi
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
assert_output_contains() {
|
|
30
|
+
local desc="$1" needle="$2"
|
|
31
|
+
shift 2
|
|
32
|
+
local output
|
|
33
|
+
output=$("$@" 2>&1) || true
|
|
34
|
+
TESTS=$((TESTS + 1))
|
|
35
|
+
if [[ "$output" != *"$needle"* ]]; then
|
|
36
|
+
echo "FAIL: $desc"
|
|
37
|
+
echo " expected to contain: $needle"
|
|
38
|
+
echo " in: ${output:0:300}"
|
|
39
|
+
FAILURES=$((FAILURES + 1))
|
|
40
|
+
else
|
|
41
|
+
echo "PASS: $desc"
|
|
42
|
+
fi
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
# --- Test: --help exits 0 ---
|
|
46
|
+
assert_exit "--help exits 0" 0 "$RUN_PLAN" --help
|
|
47
|
+
|
|
48
|
+
# --- Test: -h exits 0 ---
|
|
49
|
+
assert_exit "-h exits 0" 0 "$RUN_PLAN" -h
|
|
50
|
+
|
|
51
|
+
# --- Test: no args exits 1 ---
|
|
52
|
+
assert_exit "no args exits 1" 1 "$RUN_PLAN"
|
|
53
|
+
|
|
54
|
+
# --- Test: nonexistent plan file exits 1 ---
|
|
55
|
+
assert_exit "nonexistent plan exits 1" 1 "$RUN_PLAN" /tmp/nonexistent-plan-file-abc123.md
|
|
56
|
+
|
|
57
|
+
# --- Test: help output mentions run-plan ---
|
|
58
|
+
assert_output_contains "help mentions run-plan" "run-plan" "$RUN_PLAN" --help
|
|
59
|
+
|
|
60
|
+
# --- Test: help output mentions --mode ---
|
|
61
|
+
assert_output_contains "help mentions --mode" "--mode" "$RUN_PLAN" --help
|
|
62
|
+
|
|
63
|
+
# --- Test: help output mentions headless ---
|
|
64
|
+
assert_output_contains "help mentions headless" "headless" "$RUN_PLAN" --help
|
|
65
|
+
|
|
66
|
+
# --- Test: help output mentions --resume ---
|
|
67
|
+
assert_output_contains "help mentions --resume" "--resume" "$RUN_PLAN" --help
|
|
68
|
+
|
|
69
|
+
# --- Test: help output mentions --on-failure ---
|
|
70
|
+
assert_output_contains "help mentions --on-failure" "--on-failure" "$RUN_PLAN" --help
|
|
71
|
+
|
|
72
|
+
# --- Test: help output mentions --mab ---
|
|
73
|
+
assert_output_contains "help mentions --mab" "--mab" "$RUN_PLAN" --help
|
|
74
|
+
|
|
75
|
+
# --- Test: --resume without state file exits 1 ---
|
|
76
|
+
TMPDIR_RESUME=$(mktemp -d)
|
|
77
|
+
trap 'rm -rf "$TMPDIR_RESUME"' EXIT
|
|
78
|
+
assert_exit "--resume without state file exits 1" 1 "$RUN_PLAN" --resume --worktree "$TMPDIR_RESUME"
|
|
79
|
+
|
|
80
|
+
echo ""
|
|
81
|
+
echo "Results: $((TESTS - FAILURES))/$TESTS passed"
|
|
82
|
+
if [[ $FAILURES -gt 0 ]]; then
|
|
83
|
+
echo "FAILURES: $FAILURES"
|
|
84
|
+
exit 1
|
|
85
|
+
fi
|
|
86
|
+
echo "ALL PASSED"
|