fix: v0.46.0 — deep-audit round 2 (standard ids, SARIF, tara/qualify/audit-pack) - #84
Merged
SoundMatt merged 8 commits intoJul 29, 2026
Conversation
x-FuSa spec §2.9 MUST: tool.driver.name = the §1.1 tool name ("go-FuSa"),
not the "gofusa" binary name. check --format sarif hardcoded the binary
name instead, so the SARIF tool identity diverged from every other JSON
document's "tool" field (which already correctly emits "go-FuSa"),
violating §2.9's format-invariance rule in spirit.
Adds a regression test asserting tool.driver.name == "go-FuSa" in the
rendered SARIF log.
Closes #81
Signed-off-by: Matt Jones <47545907+SoundMatt@users.noreply.github.com>
…#77) x-FuSa spec §2.4.1 MUST: "standard" is a canonical lowercase id (e.g. "iso26262"), never a display string. 5 of 6 standards commands (all but slsa) passed a hand-built display string into gapreport.New instead: iso26262 -> "ISO 26262 ASIL-B" now -> "iso26262" do178 -> "DO-178C DAL-B" now -> "do178c" iec61508 -> "IEC 61508 SIL-2" now -> "iec61508" iso21434 -> "ISO 21434 CAL-1" now -> "iso21434" unece -> "UN R.155" now -> "unece-r155" iec62443 -> "iec62443" now -> "iec62443-4-2" (missing part suffix) The ASIL/SIL/DAL/CAL rating has no home in the canonical enum (§2.4.1) and is dropped from the field entirely — it remains available on each package's internal Report struct (rep.ASIL/DAL/SIL/CAL), it just never belonged in the canonical gap-report's "standard" value. iec62443's fix also adds the spec-mandated multi-part suffix identifying which IEC 62443 part is supported (this package assesses IEC 62443-4-2 per its own package doc). slsa already emitted the correct "slsa" and is unchanged. Adds/tightens a JSON-envelope regression test in each affected package asserting the exact canonical id. Closes #77 Signed-off-by: Matt Jones <47545907+SoundMatt@users.noreply.github.com>
x-FuSa spec §2.4.1 MUST: the JSON envelope's "standard" is a canonical lowercase id, never a display string. cmd_check.go/cmd_report.go wrote cfg.Project.Standard verbatim into rep.Standard, leaking go-FuSa's internal uppercase/no-space Standard enum spelling (e.g. "ISO26262") into the envelope instead of the canonical "iso26262". Adds config.Standard.CanonicalID(), the inverse of the existing internal canonicalStandard mapping, and uses it at both call sites. StandardGeneric/empty both map to "" so the omitempty envelope field is dropped rather than emitting a non-canonical value. Closes #78 Signed-off-by: Matt Jones <47545907+SoundMatt@users.noreply.github.com>
tara's --output-dir handling didn't create the target directory, unlike its sibling §9.2 evidence-artifact commands fmea/safety-case, which both already call os.MkdirAll. Running "gofusa tara --output-dir <not-yet- existing dir>" surfaced a raw "open ... no such file or directory" OS error and exited 3, instead of writing tara.json/tara.md like the other two commands do into a freshly created directory. Adds an os.MkdirAll(outDir, 0o750) call matching fmea/safety-case, and strengthens the existing TestRunTara_WithOutputDir test to stop pre-creating the output directory (which had been silently masking this exact bug) and assert both tara.json and tara.md now exist afterward. Closes #83 Signed-off-by: Matt Jones <47545907+SoundMatt@users.noreply.github.com>
§6: "<lang>fusa qualify [--dir <path>] [--format text|json] [--output
<file>]". gofusa qualify's flag set only defined -output plus the
qualification-metadata flags — passing --dir or --format failed with
"flag provided but not defined" (exit 2), including the exact
"--format json" invocation §6's own machine-contract language calls out
as required ("Any command whose JSON FuSaOps consumes MUST support
--format json").
Adds both flags: --format is validated to text/json (both currently
produce the same qualification report — the qualification suite itself
always runs the same built-in synthetic cases regardless of project
content, so there's no format-dependent content to diverge on) and
--dir now resolves a projectRoot used to default --output's location,
mirroring how every other command resolves projectRoot.
Closes #82
Signed-off-by: Matt Jones <47545907+SoundMatt@users.noreply.github.com>
…evidence (#79) x-FuSa spec §8 MUST: the pack MUST include every §1.2 input file and every §1.3 generated file that exists at the project root. EvidenceFiles was a fixed list dated before tara/hara/cyber/coupling/comp support existed, so audit-pack silently dropped tara.json, tara.md, cyber-report.json, coupling-report.json, comp-report.json, .fusa-hara.json, .fusa-dispositions.json, .fusa-problems.json, .fusa-model-trace.json, and the entire open-ended <standard>-gap-report.json family — with no warning that any of it was missing from the evidence bundle. Extends EvidenceFiles with the missing fixed-name §1.2/§1.3 files, and adds a discoverGapReports glob step for the <standard>-gap-report.json family (whose standard-id set is open-ended, so a fixed list can't enumerate it), sorted for deterministic manifest/ZIP ordering. Closes #79 Signed-off-by: Matt Jones <47545907+SoundMatt@users.noreply.github.com>
x-FuSa spec §1.6 rule 4 MUST ("Real referents only"): an entry naming a
file MUST refer to an actual file in the analyzed project, not a test
fixture mistaken for one. tara.Scan built threats[] directly and
unfiltered from cyber.Scan's findings, which legitimately include
_test.go files (security issues in test code are still worth flagging
in check's own CYBER category) — but those same findings, unfiltered,
were also becoming TARA "asset under threat" entries. This directly
contradicted the report's own summary.assetInventoryMethod text, which
already documents (correctly) that assetsInProject counts only
non-test .go files via CountProjectFiles.
tara.Scan now skips any cyber finding whose Location.File ends in
"_test.go" before building a ThreatEntry, reusing the same suffix
exclusion CountProjectFiles already applies to the assetsInProject
denominator (so assetsAnalyzed/coveragePct in summary are now internally
consistent with assetInventoryMethod's stated method too). Entry IDs
stay sequential from TARA-001 across the filtered set, with no gaps left
by excluded entries.
Closes #80
Signed-off-by: Matt Jones <47545907+SoundMatt@users.noreply.github.com>
Bumps the release version and regenerates the repo's own committed tara.json/tara.md with the fixed binary, which is itself a live demonstration of #80's fix: threats[] drops from 321 entries (318 of which were _test.go fixtures) down to the 3 real project-asset threats that were always the correct result. Closes #77, closes #78, closes #79, closes #80, closes #81, closes #82, closes #83 Signed-off-by: Matt Jones <47545907+SoundMatt@users.noreply.github.com>
|
You are seeing this message because GitHub Code Scanning has recently been set up for this repository, or this pull request contains the workflow file for the Code Scanning tool. What Enabling Code Scanning Means:
For more information about GitHub Code Scanning, check out the documentation. |
| if code != 0 { | ||
| t.Errorf("runQualify --format json: exit %d, stderr: %s", code, errBuf.String()) | ||
| } | ||
| if _, err := os.Stat(outFile); err != nil { |
| t.Errorf("runQualify --dir: exit %d, stderr: %s", code, errBuf.String()) | ||
| } | ||
| // --output not given, so the report should land under --dir. | ||
| if _, err := os.Stat(filepath.Join(dir, "qualify-report.json")); err != nil { |
| if code != 0 { | ||
| t.Errorf("unexpected exit %d: %s", code, errBuf.String()) | ||
| } | ||
| if _, err := os.Stat(filepath.Join(outDir, "tara.json")); err != nil { |
| if _, err := os.Stat(filepath.Join(outDir, "tara.json")); err != nil { | ||
| t.Errorf("tara.json not created in auto-created output dir: %v", err) | ||
| } | ||
| if _, err := os.Stat(filepath.Join(outDir, "tara.md")); err != nil { |
SoundMatt
deleted the
fix/audit-round-2-standard-ids-tara-qualify-auditpack
branch
July 29, 2026 04:37
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Fixes every genuine defect filed by the latest deep audit (issues #77–#83, all confirmed against the current x-FuSa spec text at
docs/x-fusa-spec.mdbefore fixing):tool.driver.namewas"gofusa"instead of the canonical"go-FuSa"(§2.9 MUST).standardfield is a display string, not the §2.4.1 canonical id (5 of 6 commands) #77 — 5 of 6 standards gap-report commands emitted a display string ("ISO 26262 ASIL-B") instead of the §2.4.1 canonical lowercase id instandard;iec62443was missing its required part suffix.standardfield uses internal uppercase enum instead of canonical id (§2.4.1 MUST) #78 —check/report's JSON envelopestandardfield leaked go-FuSa's internal uppercase enum spelling ("ISO26262") instead of the canonical id.tara --output-dirdidn't auto-create the target directory, unlike itsfmea/safety-casesiblings.qualifyerrored with exit 2 ("flag provided but not defined") on the spec-documented--dir/--formatflags.audit-packsilently droppedtara.json/tara.md/cyber-report.jsonand other evidence types added after its file list was last updated (§8 MUST).tara'sthreats[]was 99% sourced from_test.gofixtures, contradicting its ownassetInventoryMethodtext (§1.6 rule 4 MUST). Regenerating this repo's owntara.jsonwith the fix drops it from 321 entries (318 test fixtures) to the 3 real ones.#76 was investigated and found stale — the spec was updated to v1.15.1 (already the version pinned in
docs/x-fusa-spec.md) explicitly blessingMAJOR.MINOR.PATCHas the correctschemaVersion/specVersionformat, reversing theMAJOR.MINOR-only text the issue was filed against. No code change needed; closing separately with an explanation.Every fix has a regression test that reproduces the original bug (verified failing on the pre-fix code) and passes after.
Test plan
go build ./...go vet ./...golangci-lint run ./...— 0 issuesgo test ./... -cover— all packages pass, coverage ≥ 80% gategofusa trace --dir .— all new requirement ids traced+testedgofusa check --dir .— 0 errors (unchanged baseline)Closes #77, closes #78, closes #79, closes #80, closes #81, closes #82, closes #83