bmad-module-skill-forge 2.2.0 → 3.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 +1 -1
- package/README.md +49 -49
- package/docs/404.md +10 -8
- package/docs/_data/pinned.yaml +22 -13
- package/docs/_internal/STABILITY.md +58 -35
- package/docs/agents.md +39 -53
- package/docs/architecture.md +65 -51
- package/docs/bmad-synergy.md +53 -51
- package/docs/campaign.md +127 -75
- package/docs/concepts.md +34 -28
- package/docs/examples.md +70 -68
- package/docs/forge-auto.md +34 -31
- package/docs/getting-started.md +118 -57
- package/docs/how-it-works.md +25 -21
- package/docs/index.md +15 -15
- package/docs/skill-model.md +70 -59
- package/docs/troubleshooting.md +135 -18
- package/docs/verifying-a-skill.md +83 -57
- package/docs/why-skf.md +24 -22
- package/docs/workflows.md +274 -110
- package/package.json +18 -10
- package/src/forger/preferences.yaml +8 -1
- package/src/knowledge/agentskills-spec.md +2 -0
- package/src/knowledge/ccc-bridge.md +40 -24
- package/src/knowledge/confidence-tiers.md +9 -5
- package/src/knowledge/overview.md +3 -3
- package/src/knowledge/progressive-capability.md +8 -8
- package/src/knowledge/provenance-tracking.md +9 -5
- package/src/knowledge/qmd-registry.md +2 -2
- package/src/knowledge/skf-knowledge-index.csv +2 -2
- package/src/knowledge/skill-lifecycle.md +18 -11
- package/src/knowledge/split-body-strategy.md +0 -3
- package/src/knowledge/tool-resolution.md +4 -2
- package/src/knowledge/version-paths.md +101 -15
- package/src/module-help.csv +3 -3
- package/src/module.yaml +10 -0
- package/src/shared/data/ast-grep-recipes.yaml +608 -0
- package/src/shared/data/ide-context-files.json +30 -0
- package/src/shared/health-check.md +32 -12
- package/src/shared/references/description-guard-protocol.md +12 -9
- package/src/shared/references/feasibility-report-schema.md +19 -13
- package/src/shared/references/headless-gate-convention.md +55 -3
- package/src/shared/references/output-contract-schema.md +19 -8
- package/src/shared/references/pipeline-contracts.md +94 -29
- package/src/shared/references/tessl-review.md +77 -0
- package/src/shared/scripts/schemas/skf-analyze-result-envelope.v1.json +194 -0
- package/src/shared/scripts/schemas/skf-audit-result-envelope.v1.json +192 -0
- package/src/shared/scripts/schemas/skf-brief-result-envelope.v1.json +32 -4
- package/src/shared/scripts/schemas/skf-campaign-result-envelope.v1.json +174 -0
- package/src/shared/scripts/schemas/skf-create-skill-result-envelope.v1.json +284 -0
- package/src/shared/scripts/schemas/skf-drop-skill-result-envelope.v1.json +164 -0
- package/src/shared/scripts/schemas/skf-export-result-envelope.v1.json +160 -0
- package/src/shared/scripts/schemas/skf-quick-skill-result-envelope.v1.json +261 -0
- package/src/shared/scripts/schemas/skf-refine-architecture-result-envelope.v1.json +192 -0
- package/src/shared/scripts/schemas/skf-rename-skill-result-envelope.v1.json +179 -0
- package/src/shared/scripts/schemas/skf-setup-result-envelope.v1.json +27 -11
- package/src/shared/scripts/schemas/skf-stack-result-envelope.v1.json +176 -0
- package/src/shared/scripts/schemas/skf-test-result-envelope.v1.json +173 -0
- package/src/shared/scripts/schemas/skf-update-result-envelope.v1.json +19 -5
- package/src/shared/scripts/schemas/skf-verify-stack-result-envelope.v1.json +180 -0
- package/src/shared/scripts/schemas/skill-brief.v1.json +34 -0
- package/src/shared/scripts/schemas/workspace-detection.v1.json +1 -1
- package/src/shared/scripts/skf-atomic-write.py +30 -14
- package/src/shared/scripts/skf-build-change-manifest.py +2203 -24
- package/src/shared/scripts/skf-ccc-git-hygiene.py +532 -0
- package/src/shared/scripts/skf-check-unit-records.py +184 -0
- package/src/shared/scripts/skf-check-workspace-drift.py +538 -9
- package/src/shared/scripts/skf-classify-changed-files.py +694 -0
- package/src/shared/scripts/skf-comention-pairs.py +1333 -123
- package/src/shared/scripts/skf-compare-file-hashes.py +1 -1
- package/src/shared/scripts/skf-count-imports.py +1867 -0
- package/src/shared/scripts/skf-count-tokens.py +1 -1
- package/src/shared/scripts/skf-derive-assembly-shape.py +3 -2
- package/src/shared/scripts/skf-description-guard.py +99 -11
- package/src/shared/scripts/skf-detect-docs.py +694 -2
- package/src/shared/scripts/skf-detect-language.py +486 -107
- package/src/shared/scripts/skf-detect-registry.py +887 -0
- package/src/shared/scripts/skf-detect-scripts-assets.py +1 -1
- package/src/shared/scripts/skf-detect-tools.py +209 -27
- package/src/shared/scripts/skf-detect-workspaces.py +506 -30
- package/src/shared/scripts/skf-disqualify-candidates.py +821 -182
- package/src/shared/scripts/skf-emit-brief-result-envelope.py +69 -191
- package/src/shared/scripts/skf-emit-result-envelope.py +1604 -106
- package/src/shared/scripts/skf-enumerate-stack-skills.py +986 -117
- package/src/shared/scripts/skf-extract-public-api.py +4084 -85
- package/src/shared/scripts/skf-extraction-inventory.py +746 -0
- package/src/shared/scripts/skf-extraction-snapshot.py +539 -0
- package/src/shared/scripts/skf-fetch-temporal.py +674 -0
- package/src/shared/scripts/skf-find-cycles.py +97 -29
- package/src/shared/scripts/skf-find-test-report.py +476 -0
- package/src/shared/scripts/skf-forge-tier-rw.py +444 -203
- package/src/shared/scripts/skf-github-fetch.py +365 -0
- package/src/shared/scripts/skf-github-probe.py +661 -0
- package/src/shared/scripts/skf-hash-content.py +166 -12
- package/src/shared/scripts/skf-language-corpora.py +1 -1
- package/src/shared/scripts/skf-load-provenance.py +159 -27
- package/src/shared/scripts/skf-manifest-ops.py +1 -1
- package/src/shared/scripts/skf-merge-ccc-exclusions.py +2307 -223
- package/src/shared/scripts/skf-merge-doc-urls.py +1 -1
- package/src/shared/scripts/skf-names-present.py +221 -0
- package/src/shared/scripts/skf-pair-intersect.py +119 -28
- package/src/shared/scripts/skf-parse-gaps.py +1384 -0
- package/src/shared/scripts/skf-preapply.py +1 -1
- package/src/shared/scripts/skf-preflight.py +161 -27
- package/src/shared/scripts/skf-promote-staged.py +430 -0
- package/src/shared/scripts/skf-provenance-gap-dispatch.py +39 -7
- package/src/shared/scripts/skf-qmd-classify-collections.py +229 -45
- package/src/shared/scripts/skf-quick-batch.py +774 -0
- package/src/shared/scripts/skf-rebuild-managed-sections.py +972 -88
- package/src/shared/scripts/skf-recommend-scope-type.py +323 -156
- package/src/shared/scripts/skf-render-metadata-stats.py +156 -12
- package/src/shared/scripts/skf-render-quick-metadata.py +132 -28
- package/src/shared/scripts/skf-render-stack-metadata.py +976 -0
- package/src/shared/scripts/skf-resolve-authoritative-files.py +128 -13
- package/src/shared/scripts/skf-resolve-package.py +523 -106
- package/src/shared/scripts/skf-rewrite-skill-name.py +433 -47
- package/src/shared/scripts/skf-run-lock.py +577 -0
- package/src/shared/scripts/skf-scan-manifests.py +998 -57
- package/src/shared/scripts/skf-scan-skill-md-structure.py +1341 -37
- package/src/shared/scripts/skf-severity-classify.py +712 -108
- package/src/shared/scripts/skf-shape-detect.py +298 -204
- package/src/shared/scripts/skf-shard-body.py +9 -8
- package/src/shared/scripts/skf-skill-inventory.py +2412 -89
- package/src/shared/scripts/skf-skills-module.py +472 -0
- package/src/shared/scripts/skf-source-tree.py +1796 -0
- package/src/shared/scripts/skf-structural-diff.py +670 -119
- package/src/shared/scripts/skf-tessl-review.py +706 -0
- package/src/shared/scripts/skf-update-active-symlink.py +5 -5
- package/src/shared/scripts/skf-update-run-state.py +624 -0
- package/src/shared/scripts/skf-validate-brief-inputs.py +92 -29
- package/src/shared/scripts/skf-validate-brief-schema.py +4 -1
- package/src/shared/scripts/skf-validate-feasibility-report.py +577 -66
- package/src/shared/scripts/skf-validate-frontmatter.py +103 -26
- package/src/shared/scripts/skf-validate-output.py +712 -64
- package/src/shared/scripts/skf-validate-pins.py +1 -1
- package/src/shared/scripts/skf-verify-no-trace.py +116 -10
- package/src/shared/scripts/skf-verify-provenance-completeness.py +2919 -54
- package/src/shared/scripts/skf-write-skill-brief.py +367 -19
- package/src/shared/tool-requirements.yaml +201 -0
- package/src/skf-analyze-source/SKILL.md +41 -36
- package/src/skf-analyze-source/assets/skill-brief-schema.md +7 -8
- package/src/skf-analyze-source/customize.toml +36 -24
- package/src/skf-analyze-source/references/auto-docs-only.md +58 -20
- package/src/skf-analyze-source/references/continue.md +2 -13
- package/src/skf-analyze-source/references/discover-additional-source.md +147 -0
- package/src/skf-analyze-source/references/generate-briefs.md +121 -55
- package/src/skf-analyze-source/references/headless-contract.md +42 -15
- package/src/skf-analyze-source/references/identify-units.md +96 -110
- package/src/skf-analyze-source/references/init.md +73 -71
- package/src/skf-analyze-source/references/map-and-detect.md +123 -105
- package/src/skf-analyze-source/references/map-unit-exports.md +68 -0
- package/src/skf-analyze-source/references/recommend.md +51 -70
- package/src/skf-analyze-source/references/scan-project.md +60 -84
- package/src/skf-analyze-source/references/scan-root.md +39 -0
- package/src/skf-analyze-source/references/step-auto-scope-coexistence.md +47 -0
- package/src/skf-analyze-source/references/step-auto-scope-corpora.md +53 -0
- package/src/skf-analyze-source/references/step-auto-scope-split.md +91 -0
- package/src/skf-analyze-source/references/step-auto-scope.md +208 -293
- package/src/skf-analyze-source/references/step-shape-detect.md +14 -12
- package/src/skf-analyze-source/references/unit-detection-heuristics.md +37 -42
- package/src/skf-audit-skill/SKILL.md +43 -51
- package/src/skf-audit-skill/assets/drift-report-template.md +27 -3
- package/src/skf-audit-skill/customize.toml +41 -20
- package/src/skf-audit-skill/references/constituent-freshness.md +91 -0
- package/src/skf-audit-skill/references/doc-drift.md +141 -0
- package/src/skf-audit-skill/references/headless-contract.md +29 -0
- package/src/skf-audit-skill/references/init.md +148 -210
- package/src/skf-audit-skill/references/re-index.md +96 -108
- package/src/skf-audit-skill/references/report.md +96 -33
- package/src/skf-audit-skill/references/semantic-diff.md +27 -18
- package/src/skf-audit-skill/references/severity-classify.md +79 -65
- package/src/skf-audit-skill/references/severity-rules.md +15 -6
- package/src/skf-audit-skill/references/structural-diff.md +75 -90
- package/src/skf-audit-skill/references/upstream-checkout.md +77 -0
- package/src/skf-audit-skill/scripts/render-drift-tables.py +685 -0
- package/src/skf-brief-skill/SKILL.md +36 -25
- package/src/skf-brief-skill/assets/description-voice-examples.md +1 -1
- package/src/skf-brief-skill/assets/scope-templates.md +17 -24
- package/src/skf-brief-skill/assets/skill-brief-schema.md +29 -15
- package/src/skf-brief-skill/customize.toml +48 -20
- package/src/skf-brief-skill/references/analyze-target.md +142 -125
- package/src/skf-brief-skill/references/confirm-brief.md +10 -8
- package/src/skf-brief-skill/references/draft-checkpoint.md +36 -17
- package/src/skf-brief-skill/references/gather-intent-ratify.md +68 -0
- package/src/skf-brief-skill/references/gather-intent.md +87 -182
- package/src/skf-brief-skill/references/headless-args.md +84 -16
- package/src/skf-brief-skill/references/health-check.md +1 -1
- package/src/skf-brief-skill/references/invocation-contract.md +18 -13
- package/src/skf-brief-skill/references/portfolio-similarity-check.md +1 -1
- package/src/skf-brief-skill/references/qmd-collection-registration.md +7 -10
- package/src/skf-brief-skill/references/scope-definition.md +123 -47
- package/src/skf-brief-skill/references/step-auto-brief.md +24 -80
- package/src/skf-brief-skill/references/step-auto-validate.md +20 -121
- package/src/skf-brief-skill/references/version-resolution.md +3 -2
- package/src/skf-brief-skill/references/write-brief.md +66 -57
- package/src/skf-campaign/SKILL.md +31 -34
- package/src/skf-campaign/assets/campaign-state-schema.json +25 -4
- package/src/skf-campaign/customize.toml +47 -16
- package/src/skf-campaign/references/campaign-contracts.md +39 -29
- package/src/skf-campaign/references/campaign-directive-spec.md +4 -2
- package/src/skf-campaign/references/health-check.md +7 -16
- package/src/skf-campaign/references/step-01-setup.md +46 -84
- package/src/skf-campaign/references/step-02-strategy.md +31 -30
- package/src/skf-campaign/references/step-03-pins.md +26 -18
- package/src/skf-campaign/references/step-04-provenance.md +24 -23
- package/src/skf-campaign/references/step-05-skill-loop.md +67 -48
- package/src/skf-campaign/references/step-06-batch.md +41 -34
- package/src/skf-campaign/references/step-07-capstone.md +40 -25
- package/src/skf-campaign/references/step-08-verify.md +28 -29
- package/src/skf-campaign/references/step-09-refine.md +29 -30
- package/src/skf-campaign/references/step-10-export.md +48 -36
- package/src/skf-campaign/references/step-11-maintenance.md +31 -34
- package/src/skf-campaign/references/step-resume.md +37 -68
- package/src/skf-campaign/scripts/campaign-deps.py +57 -18
- package/src/skf-campaign/scripts/campaign-parse-manifest.py +361 -54
- package/src/skf-campaign/scripts/campaign-provenance.py +96 -53
- package/src/skf-campaign/scripts/campaign-quality-gate.py +592 -0
- package/src/skf-campaign/scripts/campaign-render-batch.py +257 -49
- package/src/skf-campaign/scripts/campaign-render-kickoff.py +343 -50
- package/src/skf-campaign/scripts/campaign-report.py +204 -37
- package/src/skf-campaign/scripts/campaign-state.py +1128 -0
- package/src/skf-campaign/scripts/campaign-status.py +10 -74
- package/src/skf-campaign/scripts/campaign-validate-pins.py +30 -3
- package/src/skf-campaign/scripts/campaign-validate-state.py +34 -4
- package/src/skf-campaign/templates/campaign-brief-template.yaml +4 -5
- package/src/skf-campaign/templates/campaign-report-template.md +5 -1
- package/src/skf-campaign/templates/kickoff-template.md +0 -14
- package/src/skf-create-skill/SKILL.md +27 -20
- package/src/skf-create-skill/assets/compile-assembly-rules.md +6 -5
- package/src/skf-create-skill/assets/skill-sections.md +15 -5
- package/src/skf-create-skill/customize.toml +20 -8
- package/src/skf-create-skill/references/authoritative-files-protocol.md +41 -42
- package/src/skf-create-skill/references/batch-mode.md +81 -0
- package/src/skf-create-skill/references/ccc-index-check.md +27 -0
- package/src/skf-create-skill/references/compile.md +107 -29
- package/src/skf-create-skill/references/component-extraction.md +113 -91
- package/src/skf-create-skill/references/enrich.md +41 -23
- package/src/skf-create-skill/references/entry-points-by-hand.md +20 -0
- package/src/skf-create-skill/references/extract.md +200 -161
- package/src/skf-create-skill/references/extraction-patterns-by-hand.md +141 -0
- package/src/skf-create-skill/references/extraction-patterns-tracing.md +2 -2
- package/src/skf-create-skill/references/extraction-patterns.md +584 -196
- package/src/skf-create-skill/references/generate-artifacts.md +145 -93
- package/src/skf-create-skill/references/health-check.md +1 -1
- package/src/skf-create-skill/references/load-brief.md +53 -36
- package/src/skf-create-skill/references/relabel-rule.md +12 -0
- package/src/skf-create-skill/references/report.md +28 -59
- package/src/skf-create-skill/references/source-resolution-protocols.md +49 -155
- package/src/skf-create-skill/references/step-auto-shard.md +20 -93
- package/src/skf-create-skill/references/step-doc-rot.md +44 -60
- package/src/skf-create-skill/references/step-doc-sources.md +28 -19
- package/src/skf-create-skill/references/sub/ccc-discover.md +18 -7
- package/src/skf-create-skill/references/sub/fetch-docs.md +106 -59
- package/src/skf-create-skill/references/sub/fetch-temporal.md +53 -166
- package/src/skf-create-skill/references/tier-degradation-rules.md +18 -9
- package/src/skf-create-skill/references/validate.md +173 -99
- package/src/skf-create-skill/scripts/scan-doc-rot.py +232 -99
- package/src/skf-create-stack-skill/SKILL.md +29 -56
- package/src/skf-create-stack-skill/assets/metadata-contract.md +51 -0
- package/src/skf-create-stack-skill/assets/provenance-map-schema.md +15 -15
- package/src/skf-create-stack-skill/assets/stack-skill-template.md +23 -57
- package/src/skf-create-stack-skill/customize.toml +23 -12
- package/src/skf-create-stack-skill/references/compile-stack.md +57 -66
- package/src/skf-create-stack-skill/references/compose-mode-rules.md +24 -44
- package/src/skf-create-stack-skill/references/detect-integrations.md +92 -95
- package/src/skf-create-stack-skill/references/detect-manifests.md +46 -71
- package/src/skf-create-stack-skill/references/generate-output.md +138 -128
- package/src/skf-create-stack-skill/references/init.md +90 -32
- package/src/skf-create-stack-skill/references/integration-patterns.md +1 -17
- package/src/skf-create-stack-skill/references/invocation-contract.md +34 -0
- package/src/skf-create-stack-skill/references/manifest-patterns.md +32 -20
- package/src/skf-create-stack-skill/references/parallel-extract.md +112 -38
- package/src/skf-create-stack-skill/references/rank-and-confirm.md +57 -75
- package/src/skf-create-stack-skill/references/report.md +39 -33
- package/src/skf-create-stack-skill/references/validate.md +20 -39
- package/src/skf-drop-skill/SKILL.md +28 -51
- package/src/skf-drop-skill/customize.toml +44 -30
- package/src/skf-drop-skill/references/execute.md +79 -146
- package/src/skf-drop-skill/references/invocation-contract.md +64 -0
- package/src/skf-drop-skill/references/report.md +46 -30
- package/src/skf-drop-skill/references/select.md +118 -124
- package/src/skf-drop-skill/scripts/dir-sizes.py +54 -26
- package/src/skf-drop-skill/scripts/drop-roster.py +322 -0
- package/src/skf-export-skill/SKILL.md +40 -62
- package/src/skf-export-skill/assets/managed-section-format.md +14 -50
- package/src/skf-export-skill/assets/snippet-format.md +3 -1
- package/src/skf-export-skill/customize.toml +42 -13
- package/src/skf-export-skill/references/generate-snippet.md +54 -46
- package/src/skf-export-skill/references/health-check.md +2 -0
- package/src/skf-export-skill/references/invocation-contract.md +15 -0
- package/src/skf-export-skill/references/load-skill.md +88 -62
- package/src/skf-export-skill/references/manifest-rebuild.md +9 -10
- package/src/skf-export-skill/references/multi-skill-mode.md +4 -4
- package/src/skf-export-skill/references/orphan-context-detection.md +13 -5
- package/src/skf-export-skill/references/orphan-row-detection.md +31 -22
- package/src/skf-export-skill/references/package.md +15 -73
- package/src/skf-export-skill/references/preflight-snippet-root-probe.md +51 -70
- package/src/skf-export-skill/references/result-envelope.md +31 -16
- package/src/skf-export-skill/references/summary.md +41 -17
- package/src/skf-export-skill/references/token-report.md +4 -12
- package/src/skf-export-skill/references/update-context.md +118 -237
- package/src/skf-forger/SKILL.md +61 -37
- package/src/skf-forger/bmad-skill-manifest.yaml +4 -1
- package/src/skf-forger/customize.toml +43 -0
- package/src/skf-forger/references/pipeline-mode.md +73 -18
- package/src/skf-forger/scripts/forge-status.py +299 -0
- package/src/skf-forger/scripts/parse-pipeline.py +322 -54
- package/src/skf-forger/scripts/pipeline-gate.py +428 -0
- package/src/skf-forger/scripts/pipeline-journal.py +1052 -0
- package/src/skf-quick-skill/SKILL.md +54 -53
- package/src/skf-quick-skill/assets/skill-template.md +4 -2
- package/src/skf-quick-skill/customize.toml +51 -20
- package/src/skf-quick-skill/references/batch-mode.md +74 -21
- package/src/skf-quick-skill/references/compile.md +30 -31
- package/src/skf-quick-skill/references/ecosystem-check.md +7 -57
- package/src/skf-quick-skill/references/finalize.md +69 -18
- package/src/skf-quick-skill/references/halt-contract.md +41 -29
- package/src/skf-quick-skill/references/health-check.md +5 -3
- package/src/skf-quick-skill/references/quick-extract.md +114 -45
- package/src/skf-quick-skill/references/registry-resolution.md +9 -64
- package/src/skf-quick-skill/references/resolve-target.md +116 -66
- package/src/skf-quick-skill/references/write-and-validate.md +79 -40
- package/src/skf-refine-architecture/SKILL.md +43 -53
- package/src/skf-refine-architecture/customize.toml +49 -20
- package/src/skf-refine-architecture/references/compile.md +97 -54
- package/src/skf-refine-architecture/references/exit-codes.md +30 -0
- package/src/skf-refine-architecture/references/finding-storage.md +21 -0
- package/src/skf-refine-architecture/references/gap-analysis.md +101 -38
- package/src/skf-refine-architecture/references/improvements.md +14 -20
- package/src/skf-refine-architecture/references/init.md +98 -57
- package/src/skf-refine-architecture/references/issue-detection.md +32 -39
- package/src/skf-refine-architecture/references/refinement-rules.md +37 -48
- package/src/skf-refine-architecture/references/report.md +65 -54
- package/src/skf-refine-architecture/scripts/skf-check-preservation.py +1619 -0
- package/src/skf-rename-skill/SKILL.md +19 -54
- package/src/skf-rename-skill/customize.toml +32 -26
- package/src/skf-rename-skill/references/execute.md +230 -184
- package/src/skf-rename-skill/references/exit-codes.md +7 -7
- package/src/skf-rename-skill/references/health-check.md +1 -7
- package/src/skf-rename-skill/references/invocation-contract.md +25 -0
- package/src/skf-rename-skill/references/report.md +63 -52
- package/src/skf-rename-skill/references/select.md +197 -115
- package/src/skf-rename-skill/scripts/skf-validate-rename-name.py +161 -21
- package/src/skf-setup/SKILL.md +26 -26
- package/src/skf-setup/customize.toml +14 -10
- package/src/skf-setup/references/auto-index.md +50 -63
- package/src/skf-setup/references/ccc-index.md +29 -90
- package/src/skf-setup/references/detect-and-tier.md +58 -67
- package/src/skf-setup/references/health-check.md +2 -0
- package/src/skf-setup/references/invocation-contract.md +14 -0
- package/src/skf-setup/references/report.md +43 -166
- package/src/skf-setup/references/tier-rules.md +5 -5
- package/src/skf-setup/references/write-config.md +34 -57
- package/src/skf-test-skill/SKILL.md +17 -57
- package/src/skf-test-skill/assets/output-section-formats.md +33 -34
- package/src/skf-test-skill/customize.toml +27 -13
- package/src/skf-test-skill/references/coherence-check.md +134 -62
- package/src/skf-test-skill/references/coverage-check-tiers.md +35 -0
- package/src/skf-test-skill/references/coverage-check.md +217 -254
- package/src/skf-test-skill/references/detect-mode.md +5 -5
- package/src/skf-test-skill/references/external-validators.md +94 -82
- package/src/skf-test-skill/references/health-check.md +6 -7
- package/src/skf-test-skill/references/init.md +163 -88
- package/src/skf-test-skill/references/invocation-contract.md +66 -0
- package/src/skf-test-skill/references/migration-section-rules.md +5 -2
- package/src/skf-test-skill/references/report.md +162 -142
- package/src/skf-test-skill/references/score.md +80 -107
- package/src/skf-test-skill/references/scoring-rules.md +41 -155
- package/src/skf-test-skill/references/source-access-protocol.md +19 -92
- package/src/skf-test-skill/references/step-hard-gate.md +51 -33
- package/src/skf-test-skill/scripts/aggregate-coherence.py +218 -30
- package/src/skf-test-skill/scripts/build-result-context.py +287 -0
- package/src/skf-test-skill/scripts/check-metadata-coherence.py +37 -4
- package/src/skf-test-skill/scripts/combine-external-scores.py +23 -6
- package/src/skf-test-skill/scripts/compute-score.py +223 -45
- package/src/skf-test-skill/scripts/gap-ledger.py +1381 -0
- package/src/skf-test-skill/scripts/hard-gate.py +203 -0
- package/src/skf-test-skill/scripts/load-coverage-inputs.py +760 -0
- package/src/skf-test-skill/scripts/locate-export-segments.py +835 -0
- package/src/skf-test-skill/scripts/reconcile-coverage.py +273 -79
- package/src/skf-test-skill/scripts/score-signatures.py +459 -0
- package/src/skf-test-skill/scripts/stage-helper-payload.py +148 -0
- package/src/skf-test-skill/scripts/validate-inventory.py +311 -16
- package/src/skf-test-skill/scripts/verify-declared-numerator.py +127 -52
- package/src/skf-test-skill/templates/test-report-template.md +21 -15
- package/src/skf-update-skill/SKILL.md +38 -25
- package/src/skf-update-skill/customize.toml +27 -12
- package/src/skf-update-skill/references/detect-changes.md +233 -222
- package/src/skf-update-skill/references/gap-driven.md +336 -0
- package/src/skf-update-skill/references/health-check.md +31 -5
- package/src/skf-update-skill/references/init.md +250 -84
- package/src/skf-update-skill/references/invocation-contract.md +12 -0
- package/src/skf-update-skill/references/manual-section-rules.md +6 -23
- package/src/skf-update-skill/references/merge.md +180 -47
- package/src/skf-update-skill/references/re-extract.md +53 -262
- package/src/skf-update-skill/references/report.md +100 -35
- package/src/skf-update-skill/references/write.md +331 -149
- package/src/skf-update-skill/scripts/skf-new-file-diff.py +29 -7
- package/src/skf-verify-stack/SKILL.md +23 -42
- package/src/skf-verify-stack/assets/feasibility-report-template.md +11 -5
- package/src/skf-verify-stack/customize.toml +55 -22
- package/src/skf-verify-stack/references/coverage-patterns.md +17 -8
- package/src/skf-verify-stack/references/coverage.md +67 -64
- package/src/skf-verify-stack/references/exit-codes.md +21 -8
- package/src/skf-verify-stack/references/init.md +107 -62
- package/src/skf-verify-stack/references/integration-verification-rules.md +12 -13
- package/src/skf-verify-stack/references/integrations.md +106 -65
- package/src/skf-verify-stack/references/report.md +59 -42
- package/src/skf-verify-stack/references/requirements.md +32 -9
- package/src/skf-verify-stack/references/synthesize.md +53 -39
- package/src/skf-verify-stack/scripts/skf-coverage-tally.py +398 -52
- package/src/skf-verify-stack/scripts/skf-previous-report.py +330 -0
- package/src/skf-verify-stack/scripts/skf-report-delta.py +453 -49
- package/src/skf-verify-stack/scripts/skf-verdict-rollup.py +240 -27
- package/tools/cli/commands/install.js +11 -4
- package/tools/cli/commands/status.js +15 -3
- package/tools/cli/commands/update.js +11 -4
- package/tools/cli/lib/tool-check.js +320 -0
- package/tools/cli/lib/version-check.js +22 -9
- package/tools/cli/skf-cli.js +4 -1
- package/.gitattributes +0 -16
- package/.nvmrc +0 -1
- package/docs/_internal/RELEASING.md +0 -679
- package/release-audits/v1.0.0-launch-audit.md +0 -728
- package/src/skf-audit-skill/references/step-doc-drift.md +0 -177
- package/src/skf-brief-skill/references/headless-source-authority-detection.md +0 -26
- package/src/skf-campaign/manifest.yaml +0 -15
- package/src/skf-create-skill/assets/tessl-dismissal-rules.md +0 -106
- package/src/skf-create-skill/references/ecosystem-check.md +0 -74
- package/src/skf-drop-skill/references/headless-contract.md +0 -18
- package/src/skf-update-skill/references/merge-conflict-rules.md +0 -15
- package/src/skf-update-skill/references/remote-source-resolution.md +0 -98
- package/src/skf-update-skill/references/validate.md +0 -124
- package/tools/validate-docs-drift.js +0 -233
- package/tools/validate-docs-links.js +0 -665
|
@@ -1,9 +1,11 @@
|
|
|
1
1
|
---
|
|
2
2
|
nextStepFile: 'report.md'
|
|
3
|
-
outputFile: '{
|
|
4
|
-
scoringRulesFile: '{scoringRulesPath}'
|
|
3
|
+
outputFile: '{report_file}'
|
|
5
4
|
sourceAccessProtocol: 'references/source-access-protocol.md'
|
|
6
5
|
scoringScript: 'scripts/compute-score.py'
|
|
6
|
+
# §4b.1 reads the run's gaps from the gap ledger the stages recorded them in.
|
|
7
|
+
ledgerFile: '{forge_version}/test-findings-{run_id}.json'
|
|
8
|
+
gapLedgerScript: 'scripts/gap-ledger.py'
|
|
7
9
|
---
|
|
8
10
|
|
|
9
11
|
<!-- Config: communicate in {communication_language}. -->
|
|
@@ -14,126 +16,96 @@ scoringScript: 'scripts/compute-score.py'
|
|
|
14
16
|
|
|
15
17
|
Calculate the overall completeness score by aggregating coverage, coherence, and external validation category scores with the appropriate weight distribution (naive or contextual), apply the pass/fail threshold, and determine the test result.
|
|
16
18
|
|
|
17
|
-
|
|
19
|
+
**Halt envelope.** Every HALT in this step names its `halt_reason` and phase and carries exit code 1. It releases the run lock first, whatever the release prints: from `{project-root}`, run `uv run {runLockHelper} release --lock "{forge_version}/.test-skill.lock" --owner "{run_owner}"` (SKILL.md Workflow Rules). In headless mode it then writes `{"phase": "<phase>", "reason": "<the halt message>", "halt_reason": "<halt_reason>", "skill_name": "{skill_name}", "report_path": "{report_file}"}`, adding `"path"` when the halt names one, to `{run_dir}/halt.json` and runs:
|
|
18
20
|
|
|
19
|
-
|
|
20
|
-
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
**Resolve the pass threshold (precedence: CLI > pipeline default > scalar > bundled fallback):**
|
|
24
|
-
|
|
25
|
-
1. If the workflow received `--threshold=<N>` on invocation, use that integer as `effective_threshold` (CLI wins). Set `threshold_source` = `"CLI override ({N}%)"`.
|
|
26
|
-
2. Else if `{pipeline_default_threshold}` is set in workflow context (resolved by init.md §1b from the per-pipeline threshold lookup table when `{pipeline_alias}` is present), use it as `effective_threshold`. Set `threshold_source` = `"pipeline default ({pipeline_alias} → {N}%)"`.
|
|
27
|
-
3. Else if the resolved `{defaultThreshold}` workflow-context variable (from SKILL.md On Activation §3 — `workflow.default_threshold` scalar, default `80`) is set, use it as `effective_threshold`. Set `threshold_source` = `"workflow default ({N}%)"`.
|
|
28
|
-
4. Else fall back to `80` (the bundled default — this branch should be unreachable when SKILL.md resolution ran correctly, but keeps the step robust if customize.toml resolution failed silently). Set `threshold_source` = `"bundled fallback (80%)"`.
|
|
21
|
+
```bash
|
|
22
|
+
uv run {emitEnvelopeHelper} emit-halt --workflow skf-test-skill --run-dir "{run_dir}" --target stderr < "{run_dir}/halt.json"
|
|
23
|
+
```
|
|
29
24
|
|
|
30
|
-
|
|
25
|
+
Display the line it prints, as the run's last line, then stop. If the emitter exits non-zero or prints no line, display the halt message alone. An interactive HALT displays its message and emits nothing.
|
|
31
26
|
|
|
32
|
-
|
|
27
|
+
### 1. Read the Pass Threshold
|
|
33
28
|
|
|
34
|
-
|
|
29
|
+
`{scoringScript}` owns the category weights, their redistribution and every verdict rule; this step sets its flags, hands it the score files and reads its output.
|
|
35
30
|
|
|
36
|
-
|
|
31
|
+
**The pass threshold was resolved once, at init** (init.md §1b, precedence: CLI > pipeline default > scalar > bundled fallback), and init.md §6c wrote it into the report. Read `threshold` and `thresholdSource` from the `{outputFile}` frontmatter and bind `effective_threshold` ← `threshold` as a number (without its `%`) and `threshold_source` ← `thresholdSource`. Never resolve the precedence again here: the frontmatter keeps what a long run's context may lose.
|
|
37
32
|
|
|
38
|
-
|
|
33
|
+
Pass `effective_threshold` into the scoring-input JSON's `threshold` field in §3a. The CLI flag, pipeline default, and the scalar all feed the same downstream field; the script does not need to know which layer supplied the value.
|
|
39
34
|
|
|
40
|
-
|
|
41
|
-
- Export Coverage: {percentage}%
|
|
42
|
-
- Signature Accuracy: {percentage}% or N/A (Quick tier)
|
|
43
|
-
- Type Coverage: {percentage}% or N/A (Quick tier)
|
|
35
|
+
### 2. The Category Score Files
|
|
44
36
|
|
|
45
|
-
|
|
46
|
-
- Combined Coherence: {percentage}% (contextual mode only)
|
|
47
|
-
- Or: not scored (naive mode — weight redistributed)
|
|
37
|
+
The category scores are never read back out of the report: each is the output file of the script that computed it, in the run folder `{run_dir}` (init.md §6b), and §3b hands the files to the scoring script by path:
|
|
48
38
|
|
|
49
|
-
|
|
50
|
-
-
|
|
51
|
-
-
|
|
39
|
+
- `coverage.json`: Export Coverage (coverage-check §2c)
|
|
40
|
+
- `signatures.json`: Signature Accuracy and Type Coverage (coverage-check §2b; there is none at Quick tier, for a docs-only skill, at States 2 to 5, or for a stack or a reference app)
|
|
41
|
+
- `coherence.json`: the combined coherence (coherence-check §5c; contextual mode only)
|
|
42
|
+
- `external.json`: the external validation score (external-validators §4; its `externalScore` is null when neither validator scored)
|
|
43
|
+
- `surface.json`: at State 2, the provenance-map and metadata counts behind the State 2 undercount deduction (coverage-check §2)
|
|
52
44
|
|
|
53
45
|
### 3. Apply Weight Distribution
|
|
54
46
|
|
|
55
47
|
**Read testMode from {outputFile} frontmatter.**
|
|
56
48
|
|
|
57
|
-
#### 2b. Apply State 2 Undercount Deduction (pre-script)
|
|
58
|
-
|
|
59
|
-
If `analysis_confidence == 'provenance-map'` (State 2) AND `metadata.json.skill_type != "stack"` AND step 3 recorded a provenance vs metadata divergence > 5% (see §4b in step 3), apply a 10-point deduction to `exportCoverage` BEFORE building the scoring input:
|
|
60
|
-
|
|
61
|
-
```
|
|
62
|
-
exportCoverage_adjusted = max(0, exportCoverage - 10)
|
|
63
|
-
```
|
|
64
|
-
|
|
65
|
-
Record in the report: `scoring_notes: State 2 undercount risk acknowledged — 10% deduction applied to Export Coverage (raw: {N}%, adjusted: {M}%)`. Use the adjusted value as the `exportCoverage` field in §3a below. The deduction is deterministic and does not change category weights or active-category counting.
|
|
66
|
-
|
|
67
|
-
Stack skills are exempt (the `metadata.json.skill_type != "stack"` guard above; `skill_type` is loaded in step 01 and also surfaces as `stackSkill` in §3a): a stack's own barrel is empty by design, so a provenance-vs-metadata divergence on a stack reflects the barrel-vs-constituent surface difference (suppressed by §4b's stack-skill branch in step 3), not extraction undercount — deducting for it would penalize a correctly built stack.
|
|
68
|
-
|
|
69
49
|
#### 3a. Construct Scoring Input JSON
|
|
70
50
|
|
|
71
|
-
Build
|
|
51
|
+
Build the flags the script reads from workflow context, and `toolingStatus` from the `{outputFile}` frontmatter (init.md §6c wrote it), never from memory:
|
|
72
52
|
|
|
73
53
|
```json
|
|
74
54
|
{
|
|
75
55
|
"mode": "{testMode: contextual or naive}",
|
|
76
56
|
"tier": "{forge_tier: Quick, Forge, Forge+, or Deep}",
|
|
77
|
-
"docsOnly": "{true if docs_only_mode
|
|
57
|
+
"docsOnly": "{true if docs_only_mode is set (coverage-check §0), else false}",
|
|
78
58
|
"state2": "{true if analysis_confidence is provenance-map, else false}",
|
|
79
59
|
"stackSkill": "{true if metadata.json.skill_type == 'stack', else false}",
|
|
80
60
|
"referenceApp": "{true if metadata.json.scope_type == 'reference-app', else false}",
|
|
81
|
-
"
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
"typeCoverage": "{type_coverage_percentage or null if N/A}",
|
|
85
|
-
"coherence": "{combined_coherence_percentage or null if naive mode}",
|
|
86
|
-
"externalValidation": "{external_validation_score or null if N/A}"
|
|
87
|
-
},
|
|
88
|
-
"threshold": "{effective_threshold from §1 — CLI --threshold wins, then pipeline default, then workflow.default_threshold scalar, then 80}",
|
|
89
|
-
"analysisConfidence": "{resolved analysis confidence — 'degraded' when python3/frontmatter validator missing; else full/provenance-map/metadata-only/remote-only/docs-only; omit if unknown}",
|
|
90
|
-
"toolingStatus": "{a missing-helper marker like 'python3-missing' or 'frontmatter-validator-missing' when a helper is unavailable, else omit}"
|
|
61
|
+
"threshold": "{effective_threshold from §1}",
|
|
62
|
+
"analysisConfidence": "{analysis_confidence: full, provenance-map, metadata-only, remote-only or docs-only}",
|
|
63
|
+
"toolingStatus": "{toolingStatus from the {outputFile} frontmatter: ok, or frontmatter-validator-timeout}"
|
|
91
64
|
}
|
|
92
65
|
```
|
|
93
66
|
|
|
94
|
-
**Important:**
|
|
67
|
+
**Important:** the flags are bare booleans (`true`, not `"true"`) and the threshold a number. Always pass `toolingStatus`: any value other than `ok` fires Cap 1 (§3d). `analysisConfidence` names the source access only, never tooling health. Read `metadata.json.skill_type` and `metadata.json.scope_type` from `{resolved_skill_package}/metadata.json`: a stack (`stackSkill`) and a reference app (`referenceApp`, which documents wiring patterns, not library export signatures) have no Signature Accuracy or Type Coverage, and the script redistributes their weights. With no local source (`analysisConfidence` `metadata-only` or `remote-only`, States 3 and 4) it skips both categories at any tier, as it does at Quick tier, for `docsOnly` and for `state2`.
|
|
95
68
|
|
|
96
69
|
#### 3b. Run the Scoring Script
|
|
97
70
|
|
|
71
|
+
Pass the §3a JSON and the score files that exist: `--signatures` when coverage-check scored the signatures, `--coherence` in contextual mode, and `--surface` at State 2:
|
|
72
|
+
|
|
98
73
|
```bash
|
|
99
|
-
|
|
74
|
+
uv run {scoringScript} --json-input '<the §3a JSON>' --coverage "{run_dir}/coverage.json" [--signatures "{run_dir}/signatures.json"] [--coherence "{run_dir}/coherence.json"] --external "{run_dir}/external.json" [--surface "{run_dir}/surface.json"] > "{run_dir}/score.json"
|
|
100
75
|
```
|
|
101
76
|
|
|
102
|
-
Where `{scoringScript}` is the path resolved from the frontmatter variable (relative to the skill root, i.e., the skf-test-skill/ directory).
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
- `weights
|
|
106
|
-
- `weightedScores
|
|
107
|
-
- `totalScore
|
|
108
|
-
- `threshold
|
|
109
|
-
- `result
|
|
110
|
-
- `activeCategories
|
|
111
|
-
- `skippedCategories
|
|
112
|
-
- `skipReasons
|
|
113
|
-
- `weightSum
|
|
114
|
-
- `inconclusiveReasons
|
|
115
|
-
-
|
|
116
|
-
|
|
117
|
-
- `
|
|
118
|
-
- `
|
|
119
|
-
- `
|
|
77
|
+
Where `{scoringScript}` is the path resolved from the frontmatter variable (relative to the skill root, i.e., the skf-test-skill/ directory).
|
|
78
|
+
|
|
79
|
+
Read its output from `{run_dir}/score.json`, where the report step's result contract reads `activeCategories` and `inconclusiveReasons` too. The script returns:
|
|
80
|
+
- `weights`: final redistributed weights per category
|
|
81
|
+
- `weightedScores`: weighted contribution per category
|
|
82
|
+
- `totalScore`: the overall completeness score
|
|
83
|
+
- `threshold`: the threshold used
|
|
84
|
+
- `result`: `"PASS"`, `"FAIL"`, or **`"INCONCLUSIVE"`** (the minimum-evidence floor)
|
|
85
|
+
- `activeCategories`: list of categories that were scored
|
|
86
|
+
- `skippedCategories`: list of categories that were skipped
|
|
87
|
+
- `skipReasons`: why each category was skipped
|
|
88
|
+
- `weightSum`: sum of final weights (should be ~100)
|
|
89
|
+
- `inconclusiveReasons`: only present when `result == "INCONCLUSIVE"`; explains which floor clause tripped
|
|
90
|
+
- `state2Deduction` and `scoringNotes`: present when the State 2 undercount deduction was weighed (`applied` says whether it lowered Export Coverage) and when a note applies
|
|
91
|
+
- **Verdict-override group**: present as an atomic set of four keys only when a post-score cap or the threshold fallback engaged (§3d/§4b are applied by the script, not re-derived here):
|
|
92
|
+
- `effectiveResult`: the **final verdict** after caps + fallback (`"PASS"` / `"FAIL"`); read this as the outcome for §4 to §8
|
|
93
|
+
- `capReason`: string describing the cap(s) that fired, or `null`
|
|
94
|
+
- `thresholdFallback`: `true` when the FAIL→PASS-at-80-floor fallback fired
|
|
95
|
+
- `originalThreshold`: the pre-fallback threshold when `thresholdFallback` is `true`, else `null`
|
|
120
96
|
- When the group is **absent**, no cap or fallback engaged and `result` is the final verdict.
|
|
121
97
|
|
|
122
|
-
Use these values for Section 4 (pass/fail/inconclusive) and Section 6 (output formatting). **The script owns the minimum-evidence floor, both post-score caps, and the threshold fallback
|
|
123
|
-
|
|
124
|
-
#### 3c. Fallback (if script execution fails)
|
|
125
|
-
|
|
126
|
-
**First distinguish "the script could not run" from "the script rejected the input" — they take opposite paths.**
|
|
98
|
+
Use these values for Section 4 (pass/fail/inconclusive) and Section 6 (output formatting). **The script owns the minimum-evidence floor, the State 2 deduction, both post-score caps, and the threshold fallback: everywhere below, read its emitted fields (`result`, `effectiveResult`, `capReason`, `thresholdFallback`, `scoringNotes`) and never recompute a verdict, cap, deduction or threshold decision.** The final verdict is `effectiveResult` when the override group is present, otherwise `result` (INCONCLUSIVE is never overridden).
|
|
127
99
|
|
|
128
|
-
|
|
100
|
+
#### 3c. If the Script Refuses the Input or Does Not Run
|
|
129
101
|
|
|
130
|
-
|
|
102
|
+
A `{"error": ..., "code": "INVALID_INPUT"}` envelope in `{run_dir}/score.json` (exit 2, or exit 1 for a payload that is not JSON) means the script ran and refused what it was given: a flag is missing, mistyped or out of range, or a score file is missing its score or holds a refused result. **Correct the §3a input, or re-run the step that writes the refused file, and run it again.** Never compute a total by hand from the numbers the script refused.
|
|
131
103
|
|
|
132
|
-
|
|
104
|
+
No envelope at all (the script file is missing, or it cannot start): HALT with its stderr (`halt_reason: "helper-failed"`, phase `score:compute`). A quality gate does not score by hand, so the run stops without a score rather than with an unchecked one.
|
|
133
105
|
|
|
134
106
|
### 3d. Read Post-Score Caps (applied by the script)
|
|
135
107
|
|
|
136
|
-
The script
|
|
108
|
+
The script settles the verdict in the one order its docstring states, with two post-score caps: **Cap 1** (any `toolingStatus` other than `ok`) and **Cap 2** (docs-only with no external validation score). It returns the settled outcome as `capReason` + `effectiveResult` (§3b). Read those fields; never recompute a cap. If `capReason` is non-null, record `scoring_notes: {capReason}` in the report. A fired cap forces the script's `PASS` into `FAIL`, never touches an INCONCLUSIVE verdict, and is never re-flipped by the threshold fallback (§4b): a capped run stays FAIL whatever the threshold. (Both caps exist because a degraded-tooling or docs-only-without-validators run has too thin an evidence base to trust a PASS; §3a passes the field Cap 1 reads.)
|
|
137
109
|
|
|
138
110
|
### 4. Determine Result (PASS / FAIL / INCONCLUSIVE)
|
|
139
111
|
|
|
@@ -144,7 +116,7 @@ IF result == "INCONCLUSIVE" — minimum-evidence floor tripped; not PASS, not FA
|
|
|
144
116
|
ELSE settled verdict = effectiveResult if the override group is present, else result (PASS or FAIL)
|
|
145
117
|
```
|
|
146
118
|
|
|
147
|
-
**INCONCLUSIVE floor clauses** (
|
|
119
|
+
**INCONCLUSIVE floor clauses** (the script's minimum-evidence floor):
|
|
148
120
|
- `active_categories < 2` (after all redistribution), OR
|
|
149
121
|
- `tier == "Quick"` AND Export Coverage is the sole scoring contributor
|
|
150
122
|
|
|
@@ -152,7 +124,7 @@ ELSE settled verdict = effectiveResult if the override group is present, else re
|
|
|
152
124
|
|
|
153
125
|
After §4 determines the result but before §5 recommends the next workflow, the script's threshold fallback may already have converted a FAIL into a PASS at the 80% floor. This step documents that quality compromise in an evidence report.
|
|
154
126
|
|
|
155
|
-
|
|
127
|
+
Read the script's fields:
|
|
156
128
|
|
|
157
129
|
- `thresholdFallback == true` → the fallback fired; `effectiveResult` is `"PASS"` and `originalThreshold` holds the pre-fallback threshold.
|
|
158
130
|
- `thresholdFallback` absent or `false` → no fallback; the settled verdict from §4 stands.
|
|
@@ -164,17 +136,21 @@ The rule the script encodes (documented for interpretation): when `result == "FA
|
|
|
164
136
|
3. Set `effective_threshold = 80` for use by §5/§6/§7/§8.
|
|
165
137
|
4. Generate the evidence report (§4b.1 below).
|
|
166
138
|
|
|
167
|
-
The
|
|
139
|
+
The `{totalScore}` used in the report below is the script's raw `totalScore`.
|
|
168
140
|
|
|
169
141
|
#### 4b.1 Generate Evidence Report
|
|
170
142
|
|
|
171
143
|
Write the evidence report to `{forge_version}/evidence-report-fallback.md`. The report documents the quality compromise for audit purposes.
|
|
172
144
|
|
|
173
|
-
**Read gap
|
|
145
|
+
**Read the gaps from the gap ledger**, not from the report's sections: the stages recorded every gap they found in `{ledgerFile}`, and the hard gate passed, so none is Critical or High. The script orders and counts them (`{gapLedgerScript}` resolves relative to the skill root):
|
|
174
146
|
|
|
175
|
-
|
|
147
|
+
```bash
|
|
148
|
+
uv run {gapLedgerScript} render --ledger "{ledgerFile}"
|
|
149
|
+
```
|
|
150
|
+
|
|
151
|
+
Exit 0: write its output unchanged under **Findings Preventing Higher Threshold**: the totals, the Remediation Summary and one entry per gap, by severity. A render that exits 1 prints its error on stderr: write that line there instead and continue, since the evidence report does not decide the verdict.
|
|
176
152
|
|
|
177
|
-
**Check for
|
|
153
|
+
**Check for prior remediation:** glob `{forge_version}/test-report-{skill_name}-*.md` for a prior test report. If found, note the path — this implies remediation was attempted between runs. If not found, note "first test run — no prior remediation cycle".
|
|
178
154
|
|
|
179
155
|
**Evidence report template:**
|
|
180
156
|
|
|
@@ -196,10 +172,7 @@ Write the evidence report to `{forge_version}/evidence-report-fallback.md`. The
|
|
|
196
172
|
|
|
197
173
|
## Findings Preventing Higher Threshold
|
|
198
174
|
|
|
199
|
-
{
|
|
200
|
-
- **{GAP-NNN}: {title}** — Severity: {severity}, Category: {category}
|
|
201
|
-
|
|
202
|
-
{Count: N critical, M high, P medium, Q low, R info findings}
|
|
175
|
+
{the output of the render command above, unchanged}
|
|
203
176
|
|
|
204
177
|
## Remediation Context
|
|
205
178
|
|
|
@@ -209,12 +182,9 @@ A prior test run was found at `{prior_report_path}`, indicating remediation was
|
|
|
209
182
|
{If no prior test report:}
|
|
210
183
|
No prior test report found for this skill version — this is the first test run.
|
|
211
184
|
|
|
212
|
-
{If post-score cap was active:}
|
|
213
|
-
**Note:** Score was capped due to {cap_reason}. Address tooling limitations to test at the higher threshold.
|
|
214
|
-
|
|
215
185
|
## Conclusion
|
|
216
186
|
|
|
217
|
-
Skill accepted at 80% floor (original target: {original_threshold}%). The
|
|
187
|
+
Skill accepted at 80% floor (original target: {original_threshold}%). The findings above prevented meeting the higher threshold. Review and address findings before the next pipeline run to achieve the {original_threshold}% target.
|
|
218
188
|
```
|
|
219
189
|
|
|
220
190
|
Record `evidence_report_path: '{forge_version}/evidence-report-fallback.md'` in workflow context for use by §6/§7/§8 and by report.md.
|
|
@@ -225,10 +195,11 @@ Based on the **settled verdict** (§4 — `effectiveResult` when the override gr
|
|
|
225
195
|
|
|
226
196
|
**IF PASS:**
|
|
227
197
|
- `nextWorkflow: 'export-skill'` — skill is ready for export
|
|
228
|
-
- **Drift override:** if
|
|
229
|
-
|
|
198
|
+
- **Drift override:** if the `{outputFile}` frontmatter's `workspaceDrift`
|
|
199
|
+
is `overridden` (init.md §5b wrote it when the user passed
|
|
230
200
|
`--allow-workspace-drift` AND the workspace HEAD did not match
|
|
231
|
-
`metadata.source_commit
|
|
201
|
+
`metadata.source_commit`; the flag on a clean tree leaves it `ok`), the
|
|
202
|
+
PASS is a **conditional PASS**:
|
|
232
203
|
- Write `testResult: 'pass-with-drift'` to the output frontmatter instead of
|
|
233
204
|
bare `'pass'`. The result contract (§4c of step 6) mirrors the same
|
|
234
205
|
value.
|
|
@@ -245,9 +216,9 @@ Based on the **settled verdict** (§4 — `effectiveResult` when the override gr
|
|
|
245
216
|
**IF INCONCLUSIVE:**
|
|
246
217
|
- `nextWorkflow: 'manual-review'` — evidence base is insufficient to grade the skill automatically. The test report records `inconclusiveReasons` from the scoring script. Surface to the user — do not auto-recommend export or update.
|
|
247
218
|
|
|
248
|
-
### 6.
|
|
219
|
+
### 6. Write the Completeness Score Section
|
|
249
220
|
|
|
250
|
-
|
|
221
|
+
Write the **Completeness Score** section in place of the template's `## Completeness Score` heading and the placeholder comment under it, in `{outputFile}`:
|
|
251
222
|
|
|
252
223
|
```markdown
|
|
253
224
|
## Completeness Score
|
|
@@ -277,11 +248,14 @@ Append the **Completeness Score** section to `{outputFile}`:
|
|
|
277
248
|
**Threshold Fallback:** scored {totalScore}% against {original_threshold}% target — accepted at 80% floor. Evidence report: {evidence_report_path}
|
|
278
249
|
**Weight Distribution:** {naive (redistributed) | contextual (full)}
|
|
279
250
|
**Tier Adjustment:** {none | Quick tier — signature and type coverage not scored}
|
|
280
|
-
**External Validators:** {
|
|
251
|
+
**External Validators:** {skill-check and Tessl Review | skill-check only | Tessl Review only | none — weight redistributed} (from `{external_tools_used}`; `tessl` is Tessl Review)
|
|
281
252
|
**Analysis Confidence:** {full | provenance-map | metadata-only | remote-only | docs-only}
|
|
253
|
+
**Tooling Status:** {ok | frontmatter-validator-timeout}
|
|
254
|
+
{If the script returned `scoringNotes` or a `capReason`:}
|
|
255
|
+
**Scoring Notes:** {each entry of `scoringNotes`, and `capReason`}
|
|
282
256
|
```
|
|
283
257
|
|
|
284
|
-
If `analysis_confidence` is not `full`,
|
|
258
|
+
If `analysis_confidence` is not `full`, add a degradation notice at the end of the Completeness Score section. **The notice must be confidence-aware** (see the degradation notice rules in `{sourceAccessProtocol}`):
|
|
285
259
|
|
|
286
260
|
```markdown
|
|
287
261
|
### Access Degradation Notice
|
|
@@ -294,12 +268,11 @@ If `analysis_confidence` is not `full`, append a degradation notice. **The notic
|
|
|
294
268
|
### 7. Update Output Frontmatter
|
|
295
269
|
|
|
296
270
|
Update `{outputFile}` frontmatter:
|
|
297
|
-
- `testResult: '{pass|pass-with-drift|fail|inconclusive}'` (lowercase; mirrors the **settled verdict
|
|
271
|
+
- `testResult: '{pass|pass-with-drift|fail|inconclusive}'` (lowercase; mirrors the **settled verdict**, `effectiveResult` when the override group is present, else `result`, with `pass-with-drift` substituted for `pass` when the frontmatter's `workspaceDrift` is `overridden`: see the §5 drift override)
|
|
298
272
|
- `score: '{total}%'`
|
|
299
|
-
- `threshold: '{threshold}%'`
|
|
300
|
-
- `thresholdSource: '{threshold_source}'`
|
|
273
|
+
- `threshold: '{threshold}%'`: the threshold the verdict was settled against (80 after a threshold fallback); `thresholdSource` keeps what init.md wrote
|
|
301
274
|
- When `threshold_fallback` is true, add: `thresholdFallback: true`, `originalThreshold: '{original_threshold}%'`, `evidenceReportPath: '{evidence_report_path}'`
|
|
302
|
-
- `analysisConfidence: '{full|
|
|
275
|
+
- `analysisConfidence: '{full|provenance-map|metadata-only|remote-only|docs-only}'`
|
|
303
276
|
- `nextWorkflow: '{export-skill|update-skill|manual-review}'`
|
|
304
277
|
- Append `'score'` to `stepsCompleted`
|
|
305
278
|
|
|
@@ -311,5 +284,5 @@ Report the completeness score to the user: the total percentage and PASS/FAIL ve
|
|
|
311
284
|
|
|
312
285
|
Then proceed to the gap report.
|
|
313
286
|
|
|
314
|
-
|
|
287
|
+
`stepsCompleted` now ends with `'score'` (§7 appended it), so load and execute {nextStepFile}.
|
|
315
288
|
|
|
@@ -2,164 +2,50 @@
|
|
|
2
2
|
|
|
3
3
|
# Scoring Rules
|
|
4
4
|
|
|
5
|
-
##
|
|
5
|
+
## Where the Scoring Rules Live
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
Scripts compute every score, so this file keeps no copy of their rules:
|
|
8
8
|
|
|
9
|
-
|
|
9
|
+
- `scripts/compute-score.py` owns the category weights (contextual and naive), the redistribution of each skipped category's weight (Quick tier, docs-only, State 2, no local source at States 3 and 4, a stack, a reference app, no external validation score), the State 2 undercount deduction, the minimum-evidence floor (INCONCLUSIVE), the two caps and the threshold fallback, in the order its docstring states. score.md sets the flags it reads and reads its verdict.
|
|
10
|
+
- `scripts/aggregate-coherence.py` owns the contextual coherence split between reference validity and integration completeness; coherence-check.md §5 decides which integration patterns are complete.
|
|
11
|
+
- `scripts/reconcile-coverage.py` computes Export Coverage on every branch; a docs-only skill takes its `docsOnly` branch, the documentation completeness ratio coverage-check.md §2c names. `scripts/score-signatures.py` computes Signature Accuracy and Type Coverage.
|
|
10
12
|
|
|
11
|
-
|
|
12
|
-
|------------------------|--------|-------------------------------------------------------------------------------------------|
|
|
13
|
-
| Export Coverage | 36% | Percentage of source exports documented in SKILL.md |
|
|
14
|
-
| Signature Accuracy | 22% | Documented signatures match actual source signatures |
|
|
15
|
-
| Type Coverage | 14% | Types and interfaces referenced are complete |
|
|
16
|
-
| Coherence (contextual) | 18% | Cross-references valid, integration patterns complete |
|
|
17
|
-
| Coherence (naive) | 0% | Not applicable — weight redistributed to other categories |
|
|
18
|
-
| External Validation | 10% | Average of skill-check quality score + tessl average score (redistributed if unavailable) |
|
|
19
|
-
|
|
20
|
-
## Naive Mode Weight Redistribution
|
|
21
|
-
|
|
22
|
-
The following weights replace the default table for naive mode. The 18% coherence weight from the default table has been proportionally redistributed into these values. Do not re-redistribute for coherence (already handled in this table). Quick-tier redistribution (zeroing Signature Accuracy and Type Coverage) still applies as an additional step.
|
|
23
|
-
|
|
24
|
-
When running in naive mode (no coherence category):
|
|
25
|
-
- Export Coverage: 45%
|
|
26
|
-
- Signature Accuracy: 25%
|
|
27
|
-
- Type Coverage: 20%
|
|
28
|
-
- External Validation: 10%
|
|
29
|
-
|
|
30
|
-
## External Validation Unavailable
|
|
31
|
-
|
|
32
|
-
When neither skill-check nor tessl is available, redistribute the 10% external validation weight proportionally to the other active categories. When only one tool is available, use that tool's score as the external validation score.
|
|
33
|
-
|
|
34
|
-
## tessl and Split-Body Interaction
|
|
35
|
-
|
|
36
|
-
tessl evaluates SKILL.md body content only — it does not read `references/*.md` files. After split-body extraction, the tessl content score will drop significantly (e.g., 65% to 38%) because Tier 2 content is no longer inline. This is expected behavior and does not reflect actual content quality. When reporting scores for a split-body skill, note: "tessl content score reflects post-split inline content only. Use the pre-split tessl score as the content quality baseline."
|
|
37
|
-
|
|
38
|
-
## Tier-Dependent Scoring
|
|
39
|
-
|
|
40
|
-
### Quick Tier (no tools)
|
|
41
|
-
- Export Coverage: file/structure existence check only
|
|
42
|
-
- Signature Accuracy: skipped (no AST)
|
|
43
|
-
- Type Coverage: skipped (no AST)
|
|
44
|
-
- Score based on: structural completeness only
|
|
45
|
-
- Weight redistribution: skipped categories' weights (Signature Accuracy 22% + Type Coverage 14%) redistributed proportionally to remaining active categories
|
|
46
|
-
|
|
47
|
-
### Docs-Only Mode (all [EXT:...] citations, any tier)
|
|
48
|
-
|
|
49
|
-
When `docs_only_mode: true` is set by step 3 (indicating a skill where all SKILL.md citations are `[EXT:...]` format with no local source code):
|
|
50
|
-
|
|
51
|
-
- **Signature Accuracy:** Not scored (no source to compare against)
|
|
52
|
-
- **Type Coverage:** Not scored (no source to compare against)
|
|
53
|
-
- **Weight redistribution:** Same as Quick tier — Signature Accuracy (22%) and Type Coverage (14%) weights redistributed proportionally to remaining active categories
|
|
54
|
-
- **Export Coverage basis:** Documentation completeness rather than source coverage. Score = (documented_items_with_complete_descriptions / total_documented_items) * 100. A "complete" item has: description, parameters (if function/method), and return type (if function/method).
|
|
55
|
-
- **Coherence:** Standard rules for the detected mode (naive or contextual) apply unchanged
|
|
56
|
-
|
|
57
|
-
This is functionally identical to Quick tier weight redistribution but with a different coverage denominator (self-consistency instead of source comparison).
|
|
58
|
-
|
|
59
|
-
**External-validator requirement for docs-only:** docs-only mode removes two categories (Signature Accuracy, Type Coverage) from scoring. If External Validation is also unavailable, the evidence base collapses to Coverage alone (naive) or Coverage + Coherence (contextual) — which in the naive/Quick case trips the minimum-evidence floor (INCONCLUSIVE). To keep docs-only skills gradable when external validators are present but still deterministic when they are missing: **when `docsOnly: true` AND `externalValidation is null`, step 5 must cap `totalScore` at `threshold - 1` (forcing FAIL) before the INCONCLUSIVE floor is evaluated.** This prevents a docs-only skill from PASSing with only one or two redistributed categories carrying all the weight. Implement in step 5 §4 as a pre-compare cap, recorded in the report as `scoring_notes: docs-only without external validators — capped below threshold`.
|
|
60
|
-
|
|
61
|
-
### Stack Skills (Any Tier)
|
|
62
|
-
|
|
63
|
-
When `metadata.json.skill_type == "stack"` (set `stackSkill: true` in the scoring input):
|
|
64
|
-
|
|
65
|
-
- **Signature Accuracy:** N/A — a stack skill's "signature surface" is the external library API it composes (pydantic, SQLAlchemy, FastAPI, etc.), not a proprietary surface the skill authors. Grading signatures against a surface the skill does not own produces meaningless numbers.
|
|
66
|
-
- **Type Coverage:** N/A — same rationale; the type surface belongs to the external libraries.
|
|
67
|
-
- **Weight redistribution:** Same as Quick tier / docs-only / State 2 — Signature Accuracy (22%) and Type Coverage (14%) weights redistributed proportionally to remaining active categories (Export Coverage, Coherence, External Validation).
|
|
68
|
-
- **Applies regardless of detected tier** (Quick, Forge, Forge+, Deep) and is independent of `docsOnly` and `state2`. A stack skill can also be docs-only or State 2; the skip reasons combine additively (e.g. `"stack skill (external type surface) + State 2 (provenance-map)"`).
|
|
69
|
-
- **Detection:** step 5 reads `metadata.json.skill_type` from the skill package. If the value is `"stack"`, set `stackSkill: true` in the scoring input JSON.
|
|
70
|
-
|
|
71
|
-
### Reference-App Skills (Any Tier)
|
|
72
|
-
|
|
73
|
-
When `metadata.json.scope_type == "reference-app"` (set `referenceApp: true` in the scoring input):
|
|
74
|
-
|
|
75
|
-
- **Signature Accuracy:** N/A — a reference app documents wiring patterns (how surfaces are composed), not a library export surface the skill authors. There are no public-export signatures to grade against; the Pattern Surface replaces the Key API Summary (see `skf-create-skill` Reference-App Assembly Overrides).
|
|
76
|
-
- **Type Coverage:** N/A — same rationale; a reference app has no library type surface to cover. Coverage is measured as pattern-surface coverage (`stats.pattern_surfaces_documented`), not export/type coverage.
|
|
77
|
-
- **Weight redistribution:** Same as Quick tier / docs-only / State 2 / stack — Signature Accuracy (22%) and Type Coverage (14%) weights redistributed proportionally to remaining active categories (Export Coverage, Coherence, External Validation).
|
|
78
|
-
- **Applies regardless of detected tier** (Quick, Forge, Forge+, Deep) and is independent of `docsOnly` and `state2`; skip reasons combine additively. `referenceApp` and `stackSkill` are distinct scope/type signals and should not both be set for the same skill.
|
|
79
|
-
- **Detection:** step 5 reads `metadata.json.scope_type` from the skill package. If the value is `"reference-app"`, set `referenceApp: true` in the scoring input JSON. The skip reason recorded is `"reference-app (no library export signatures)"`.
|
|
80
|
-
|
|
81
|
-
### State 2 Source Access (Any Tier, Provenance-Map Only)
|
|
82
|
-
|
|
83
|
-
When source is not locally available and analysis resolves to State 2 (provenance-map baseline per source-access-protocol.md):
|
|
84
|
-
|
|
85
|
-
- **Signature Accuracy:** N/A — provenance-map stores parameters as flat string arrays; verification is string comparison only, not semantic AST verification. Type aliases (`str` vs `String`, `list` vs `List[Any]`) cannot be resolved without live source.
|
|
86
|
-
- **Type Coverage:** N/A — cannot verify type completeness without local source access for AST re-parsing.
|
|
87
|
-
- **Weight redistribution:** Same as Quick tier — Signature Accuracy (22%) and Type Coverage (14%) weights redistributed proportionally to remaining active categories (Export Coverage, Coherence, External Validation).
|
|
88
|
-
- **Applies regardless of detected tier** (including Forge, Forge+, Deep) whenever `analysis_confidence` is `provenance-map` and local source is unavailable.
|
|
89
|
-
- **Export Coverage denominator:** Uses the union of provenance-map entry names and metadata.json `exports[]` names (per source-access-protocol.md State 2 rules).
|
|
90
|
-
|
|
91
|
-
Note: When provenance-map entries are predominantly T1 (AST-verified at compilation time), the coverage and name-matching data is already at highest confidence. The N/A categories reflect the inability to re-verify at test time, not low-quality extraction data.
|
|
92
|
-
|
|
93
|
-
**State 2 undercount risk acknowledgement:** provenance-map is a cached extraction snapshot — if the source has evolved since extraction, public API adds/removes will not surface in Export Coverage (denominator is frozen to the provenance-map union). When `state2: true` AND step 3 records any provenance vs metadata divergence (e.g. union > either source by >5%), apply a flat **10% deduction** to `exportCoverage` before calling the scoring script, AND set `analysis_confidence: provenance-map` (already set) with a report note: `scoring_notes: State 2 undercount risk acknowledged — 10% deduction applied to Export Coverage`. Rationale: the skill cannot be reliably scored on a frozen denominator when the cache is known to disagree with its own metadata; prefer understating over overstating.
|
|
94
|
-
|
|
95
|
-
### Forge Tier (ast-grep)
|
|
96
|
-
- Export Coverage: AST-backed export comparison
|
|
97
|
-
- Signature Accuracy: AST-verified signature matching
|
|
98
|
-
- Type Coverage: AST-verified type completeness
|
|
99
|
-
- Full scoring formula applied
|
|
100
|
-
|
|
101
|
-
### Forge+ Tier (ast-grep + ccc)
|
|
102
|
-
- Same scoring as Forge tier — ccc provides pre-ranking but does not change scoring weights
|
|
103
|
-
- Improved extraction coverage (from ccc pre-discovery) may increase T1 count, but scoring formula is identical to Forge
|
|
104
|
-
- Full scoring formula applied
|
|
105
|
-
|
|
106
|
-
### Deep Tier (ast-grep + gh + QMD)
|
|
107
|
-
- All Forge tier checks plus:
|
|
108
|
-
- Cross-repository reference verification
|
|
109
|
-
- QMD knowledge enrichment for coherence
|
|
110
|
-
- Full scoring formula with maximum depth
|
|
111
|
-
- **Migration & Deprecation Warnings section:** If T2-future annotations exist in the enrichment data, verify that Section 4b is present in SKILL.md Tier 1 and that each warning traces to a T2 provenance citation. If no T2-future annotations exist, Section 4b should normally be absent (not empty). Presence/absence mismatch is a Medium severity gap — with one Info-severity exception for historical-migration content (completed package renames, consolidated import paths, shipped API cutovers that remain load-bearing for training-data drift remediation). See `references/coherence-check.md` §2b/§5b for the three-case rule.
|
|
112
|
-
|
|
113
|
-
## Score Calculation
|
|
114
|
-
|
|
115
|
-
```
|
|
116
|
-
score = sum(category_weight * category_score) for each category
|
|
117
|
-
category_score = (items_passing / items_total) * 100
|
|
118
|
-
```
|
|
119
|
-
|
|
120
|
-
## Coherence Score Aggregation (Contextual Mode)
|
|
121
|
-
|
|
122
|
-
```
|
|
123
|
-
reference_validity = (valid_references / total_references) * 100
|
|
124
|
-
integration_completeness = (complete_patterns / total_patterns) * 100
|
|
125
|
-
combined_coherence = (reference_validity * 0.6) + (integration_completeness * 0.4)
|
|
126
|
-
```
|
|
127
|
-
|
|
128
|
-
If no integration patterns exist, combined coherence equals reference validity.
|
|
129
|
-
|
|
130
|
-
This is the documented contract. The tally + weighted mean is computed by `scripts/aggregate-coherence.py` (invoked from coherence-check.md §5c), not by hand; the per-reference validity judgment (§4) and pattern-completeness judgment (§5) stay in the prompt, only the arithmetic is scripted.
|
|
131
|
-
|
|
132
|
-
## Result Determination
|
|
133
|
-
|
|
134
|
-
Three-state gate — **PASS / FAIL / INCONCLUSIVE**. `INCONCLUSIVE` is not PASS and not FAIL; it signals insufficient evidence to grade the skill. Downstream workflows must treat `INCONCLUSIVE` as a hard gate — do not export, do not auto-retry, surface to the human.
|
|
135
|
-
|
|
136
|
-
- **Minimum-Evidence Floor (applies before PASS/FAIL comparison):**
|
|
137
|
-
- `active_categories` = count of categories with a non-zero final weight *after* all redistribution (Quick tier, docs-only, State 2, external-validator-unavailable). Categories with a redistributed weight of 0 do not count as active, even if they received a score.
|
|
138
|
-
- **If `active_categories < 2`** → force `result: INCONCLUSIVE` with rationale `"insufficient evidence: only {N} active category"`. A single active category cannot cross-validate itself and a PASS would be a false signal.
|
|
139
|
-
- **If `tier == "Quick"` AND the sole active contributor is Export Coverage** → force `result: INCONCLUSIVE` with rationale `"Quick tier: Export Coverage alone is insufficient evidence — add a second active category by upgrading tier or enabling external validators"`. This catches the degenerate case where every signature/type/coherence/external category gets redistributed to 0 and Export Coverage is doing all the work.
|
|
140
|
-
- The floor is enforced by `scripts/compute-score.py`. The step 5 scoring step reads `result` from the script output and writes it into the test report frontmatter unchanged.
|
|
141
|
-
|
|
142
|
-
- Otherwise:
|
|
143
|
-
- score >= threshold → PASS
|
|
144
|
-
- score < threshold → FAIL
|
|
145
|
-
|
|
146
|
-
The floor is intentionally conservative: skf-test-skill grades other skills, so a false PASS has catastrophic downstream effects (polluted exports, misleading feasibility data). Falling back to INCONCLUSIVE is always preferred over a low-evidence PASS.
|
|
13
|
+
The pass threshold is `{defaultThreshold}`, unless `--threshold` or the pipeline's default overrides it (score.md §1).
|
|
147
14
|
|
|
148
15
|
## Gap Severity
|
|
149
16
|
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
|
153
|
-
|
|
154
|
-
|
|
|
155
|
-
|
|
|
156
|
-
|
|
|
157
|
-
|
|
|
158
|
-
|
|
|
159
|
-
|
|
|
160
|
-
|
|
|
161
|
-
|
|
|
162
|
-
|
|
|
163
|
-
|
|
|
164
|
-
|
|
|
165
|
-
|
|
|
17
|
+
This table is the single source of truth for classifying a gap. Every stage records each gap it finds in the gap ledger (`scripts/gap-ledger.py`, `{forge_version}/test-findings-{run_id}.json`) with the severity and the category of the row it matches. The hard gate (step 4c) blocks a run on any Critical or High gap, before scoring. A Medium, Low or Info gap never blocks. Scores come from the category metrics (a missing export lowers Export Coverage), and the pass threshold decides the verdict. Discovery testing runs after the gate, so a discovery gap of any severity is counted in the Gap Report and blocks nothing.
|
|
18
|
+
|
|
19
|
+
| Severity | Category | Criteria |
|
|
20
|
+
|----------|-----------------------------|----------|
|
|
21
|
+
| Critical | `signature-mismatch` | Wrong signature: a documented signature that differs from the source in its parameters (name, type, order, optionality) or its return type (coverage-check §2) |
|
|
22
|
+
| Critical | `fabricated-signature` | Fabricated signature: a documented export absent at the source line the skill cites for it. Decided only where ast-grep enumerated the exports at the pinned commit: the name is outside that surface, and the cited file is missing or defines no such name (coverage-check §2c) |
|
|
23
|
+
| Critical | `broken-reference` | Broken reference (contextual mode): a reference whose target does not exist, such as a file not at the stated path, a skill not in the skills output folder, a type no module declares, or a `scripts/` or `assets/` file the skill names (coherence-check §4) |
|
|
24
|
+
| High | `inaccurate-reference` | Inaccurate reference (contextual mode): the target exists but does not match, such as a type the cited module does not export, a signature that differs, or an integration pattern that does not match the implementation (coherence-check §4) |
|
|
25
|
+
| High | `reference-escape` | A reference whose real path leaves the skill, its source and, for a stack, the skills output folder (coherence-check §4) |
|
|
26
|
+
| High | `split-body-mismatch` | The SKILL.md body and a `references/` file document one export differently (coverage-check §1b) |
|
|
27
|
+
| High | `numerator-inflation` | `stats.exports_documented` equals the denominator while declared exports are absent from SKILL.md and `references/` (coverage-check §4b) |
|
|
28
|
+
| High | `structural` | Naive mode: a missing required section, an unbalanced code fence, or a documented async or sync behaviour its example contradicts (coherence-check §2.1, §2.2, §2.5) |
|
|
29
|
+
| High | `discovery` | Discovery test: at most 1 of 3 realistic prompts routed to the skill (report §4b.3) |
|
|
30
|
+
| Medium | `missing-export` | Missing export: an exported function or class the skill does not document. It lowers Export Coverage, and the threshold decides the verdict |
|
|
31
|
+
| Medium | `missing-type` | Missing type or interface documentation |
|
|
32
|
+
| Medium | `stale-documentation` | A documented export the enumerated source surface lacks that is not a fabricated signature: its cited file defines it, or no cited line could be checked (coverage-check §2c) |
|
|
33
|
+
| Medium | `migration-section` | Migration section present/absent mismatch with T2-future annotation data (Deep tier; Case 1 and Case 3 of `migration-section-rules.md`) |
|
|
34
|
+
| Medium | `metadata-drift` | Metadata drift: intra-cluster export counts diverge by more than 10% (barrel: `stats.exports_public_api` vs `exports[].length`; documented surface: `stats.exports_documented` vs the provenance-map named-export count), or denominator deflation: the re-derived source barrel exceeds `effective_denominator` by more than 25% and the brief has no `scope.tier_a_include` (coverage-check §4 and §4b) |
|
|
35
|
+
| Medium | `denominator-inflation` | Denominator inflation: the stratified-scope `scope.include` union exceeds the provenance-map entry count by more than 25% (brief missing `scope.tier_a_include`) |
|
|
36
|
+
| Medium | `scripts-assets` | A `scripts/` or `assets/` directory exists but SKILL.md has no Scripts & Assets section (coherence-check §2.7 and §4) |
|
|
37
|
+
| Medium | `integration-pattern` | Incomplete integration pattern (contextual mode): one entry of coherence-check §5's `incomplete_patterns` |
|
|
38
|
+
| Medium | `structural` | Naive mode: an opening code fence without a language tag, an exported function or method no usage-family section or reference file names, or a table row whose column count differs from its header (coherence-check §2.3, §2.4, §2.6) |
|
|
39
|
+
| Medium | `discovery` | Discovery test: 2 of 3 realistic prompts routed to the skill (report §4b.3) |
|
|
40
|
+
| Low | `scripts-assets-provenance` | Script/asset file present without provenance entry in provenance-map.json file_entries |
|
|
41
|
+
| Low | `provenance-line` | Provenance line is not the definition of an export (`line-not-definition`, coverage-check §4c) |
|
|
42
|
+
| Low | `migration-section` | Case 3 of `migration-section-rules.md` that the reviewer downgraded with an inline justification |
|
|
43
|
+
| Low | `metadata` | Missing optional metadata or examples |
|
|
44
|
+
| Low | `description` | Description trigger optimization recommended (third-person voice, negative triggers, or keyword coverage gaps), a Tessl Review description suggestion included |
|
|
45
|
+
| Low | `external-validator` | A skill-check diagnostic or a Tessl Review validation finding the run left unresolved (external-validators §5b) |
|
|
46
|
+
| Info | `observation` | Style suggestions, non-blocking observations |
|
|
47
|
+
| Info | `provenance-unverified` | Provenance line not verified: the line-check rules found no definition line (coverage-check §4c) |
|
|
48
|
+
| Info | `migration-section` | Historical migration content in Section 4b with no T2-future annotation (Case 2 of `migration-section-rules.md`) |
|
|
49
|
+
| Info | `multi-denominator` | Multi-denominator reporting: barrel and documented-surface clusters diverge by design (>10% cross-cluster) |
|
|
50
|
+
| Info | `discovery` | Discovery testing not performed (`--no-discovery`, a catalog of fewer than 2 skills, or no subagents to route the prompts): realistic prompt testing recommended before export (report §4b) |
|
|
51
|
+
| Info | `external-validator` | A Tessl Review content suggestion (advisory; one marked `(not applicable: …)` is not recorded) |
|