Release CodeTruss CLI v0.2.53 - #46
Merged
Merged
Conversation
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
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.
Syncs the 0.2.53 source from the private monorepo, byte for byte against the monorepo git objects (169 paths compared by blob hash, 0 mismatches, 0 missing).
That digest was not copied into
release-reference.json:pnpm release:artifactwas run against this tree, resolved from this repository's own lockfile, and the rebuilt archivecmps clean against the monorepo's copy, against this repo'slatestpointer, and against the bytes codetruss.com is serving right now. The samecmpagainst the published 0.2.52 archive exits 1, so the comparison is capable of failing. All three digests inrelease-reference.jsonwere re-measured off the files — archive, SBOM, and thedist/cli.cjsextracted from inside the archive — rather than transcribed.The blob-hash comparison was run a second time against the pre-sync tree as a negative control: it reported 17 mismatched paths and 3 missing, and exited 1, so a sync that silently dropped a file would not have passed.
Why this one is urgent
https://codetruss.com/downloads/codetruss-cli-latest.jsonalready advertises 0.2.53, and itsreleaseUrl—.../releases/tag/v0.2.53— currently 404s, because the release does not exist yet. Tagging this merge is what makes the advertised URL resolve.Unlike 0.2.52, this one changes behaviour
0.2.52 was three documentation corrections and a one-byte bundle delta. This is an analyzer change, and the bundle shows it:
dist/cli.cjsgoes from 819,902 to 828,029 bytes (+8,127), 4 changed lines out of 296, first difference at byte offset 207,055. If this PR claimed "no behaviour change" the bundle would contradict it.It came out of a cross-tool benchmark against ten repositories selected by a rule written before either tool ran — a corpus we did not choose — run against CodeTruss 0.2.51 and Semgrep CE. Measured on that corpus, published 0.2.51 → this release on the same machine: total findings 898 → 904, eight of ten repositories byte-identical, CRITICALs 3 → 2,
sql-injection1 → 7, HIGH-or-CRITICAL security findings 77 → 58. Zero of the 30 hand-adjudicated correct findings disappeared.A tagged template is bound parameters, not concatenation. firecrawl's
apps/api/src/db/rpc.ts:98is drizzle'sdb.execute(sql`…`)— the documented safe construction — and was reported CWE-89 CRITICAL as "untrusted input is concatenated". The rule already had this exemption for Prisma but expressed it as a method-name list, so it protected one library by name instead of the construction by shape. It now matches the shape, which covers drizzle, postgres.js, slonik, and the next library that builds queries the same way. Untagged template literals still fire, andsql.raw()is still a sink, including nested inside a tagged template.A query whose entire text is a caller-supplied parameter is now reported. uptime-kuma's
server/monitor-types/postgres.js:63was silent because a bare parameter had never counted as a "real source"; Semgrep caught it and we did not. It now reports at HIGH with a message that states what is and is not known. The narrowing came from the corpus rather than from guesswork: the argument must be the parameter itself (firecrawl'snuq.ts:1028builds its query in view and is not reported), the receiver must be database-shaped (FenwickTree.queryRangeis not a database), any same-file call site binding a constant or a tagged template suppresses it, and anonymous functions are skipped because their call sites cannot be resolved by name.Typed credentials in test paths are downgraded on the VALUE, not the path. The test-context downgrade previously reached only the generic-password pattern; it now reaches AWS/GitHub/Stripe/Anthropic/OpenAI/Google/Slack as a conjunction with a new sequence predicate, measured at zero hits across 20,000 random base62 bodies. Database URLs and PEM private-key blocks are deliberately left out of the downgrade — a real connection string or key in a test fixture is still a real leak. 25 HIGH findings became LOW; the two that did not are named in the changelog.
The frozen renderers still reproduce
The analysis profile becomes
local-registry-v5, because v4's SQL sentence no longer describes its own pass. Every superseded profile keeps a frozen Markdown renderer so receipts signed under it still verify byte-for-byte, andtest/verify-receipt.test.tspins each one by SHA-256.No previously frozen digest moved. v1
928da3c4…, v2113d62de…, v3f38a8bde…and v4288de3e2…are character-identical between the 0.2.52 and 0.2.53 trees; v56ae337ce…is added. That test is not decoration: flipping a single hex character of the v4 expected digest makes it fail withrenders 'local-registry-v4' to the exact bytes its signature covers, and the file was restored byte-exactly afterwards (the 169-path blob comparison was re-run and still reported 169 identical).No published artifact was modified
git statusunderpublic/downloads/reports nothing outsidecodetruss-cli-0.2.53.*and thelatestpointers, so 0.2.44 through 0.2.52 still carry exactly the bytes they were attested with.packages/cli/CHANGELOG.mdis 132 additions, 0 deletions; the 0.2.52, 0.2.51 and 0.2.50 sections are byte-identical to what is already published (4444, 4303 and 1895 bytes respectively).pnpm-workspace.yaml,.npmrc,pnpm-lock.yaml,package.json(root),README.mdand.github/are unchanged — the sync never writes mirror-owned files.CHANGELOG.mdat the root is regenerated frompackages/cli/CHANGELOG.md. The generator was checked by feeding it the 0.2.52 package changelog and confirming it reproduces the committed 0.2.52 root changelog byte-for-byte; run with a deliberately wrong release version it does not, so it is capable of failing. Its npm-trail sentence stays at 0.2.50, becausenpm view @codetruss/cli dist-tagsstill reportslatestas 0.2.50.Checked locally before opening
pnpm install --frozen-lockfileresolves with the lockfile untouched (the only source change topackages/cli/package.jsonis the version string).pnpm validatepasses against this branch: typecheck,release:artifact,pnpm test(35 files, 435 tests), the deterministic-package, release-verifier and changelog-policy suites,release:verify, andtest:install. The rebuilt archive reproduced5344ab8e…exactly.The release workflow's
awkextraction of the changelog entry was dry-run against the regeneratedCHANGELOG.mdand returns 114 non-empty lines, so the release note will not be install-steps-only; the sameawkfor a version with no entry returns 0 bytes, which is the case the workflow refuses to publish.One thing this release gets wrong
packages/cli/README.mdstill says receipts identify the "15-passlocal-registry-v4profile". As of this release they identifylocal-registry-v5. The README was not touched by the 0.2.53 commit, so that sentence is now false inside the shipped tarball.It is not corrected here. The 0.2.53 archive is already committed to the monorepo, already served by codetruss.com, and already advertised by the live manifest under the digest above; editing it now would mean changing bytes that are already published. It is recorded here and belongs in 0.2.54 — the same way the 0.2.51 changelog error was left standing and corrected in the following entry rather than rewritten.
🤖 Generated with Claude Code