Skip to content

fix(deps): patch 5 high-severity transitive vulnerabilities#583

Merged
carlos-alm merged 7 commits intomainfrom
fix/deps-audit-security
Mar 24, 2026
Merged

fix(deps): patch 5 high-severity transitive vulnerabilities#583
carlos-alm merged 7 commits intomainfrom
fix/deps-audit-security

Conversation

@carlos-alm
Copy link
Copy Markdown
Contributor

Summary

  • Run npm audit fix to resolve all 5 high-severity transitive vulnerabilities (hono, @hono/node-server, express-rate-limit, minimatch, tar)
  • Update @biomejs/biome 2.4.7 → 2.4.8, vitest + @vitest/coverage-v8 4.1.0 → 4.1.1
  • Add dependency audit report (generated/deps-audit/DEPS_AUDIT_2026-03-24.md)

Vulnerabilities fixed

Package Severity Advisory
hono ≤4.12.6 HIGH (5 CVEs) Auth bypass, file access, cookie injection, SSE injection, prototype pollution
@hono/node-server <1.19.10 HIGH Static path auth bypass via encoded slashes
express-rate-limit 8.2.0–8.2.1 HIGH IPv4-mapped IPv6 rate limit bypass
minimatch <3.1.4 HIGH ReDoS via nested extglobs
tar ≤7.5.10 HIGH Hardlink/symlink path traversal

All are transitive dependencies (3 via @modelcontextprotocol/sdk). No breaking changes.

Test plan

  • npm audit reports 0 vulnerabilities after fix
  • npm test passes (2033 passed, 16 skipped, 2 pre-existing EPERM failures unrelated)
  • No direct dependency changes — only lock file updates

npm audit fix resolves all 5 high-severity vulns (hono, @hono/node-server,
express-rate-limit, minimatch, tar) and updates biome 2.4.8, vitest 4.1.1.
@claude
Copy link
Copy Markdown

claude bot commented Mar 24, 2026

Claude finished @carlos-alm's task —— View job


Security Dependency Review Complete ✅

Root Cause Analysis

Problem Being Solved: 5 high-severity transitive vulnerabilities in web server components (hono, express-rate-limit) and file processing utilities (tar, minimatch) with documented CVEs including auth bypasses, file access vulnerabilities, and ReDoS attacks.
Why This Approach: npm audit fix is the standard, safe approach for patching transitive vulnerabilities without breaking changes. All fixes are minor version updates within semver ranges.
Risk Assessment: ✅ LOW RISK — Only lock file changes, no direct dependencies modified, comprehensive audit report generated.

Backlog Compliance

  • Zero-dep: ✅ — No new runtime dependencies added, only lock file version updates
  • Foundation-aligned: ✅ — Security fixes align with infrastructure reliability (P4: zero-cost core)
  • Problem-fit: 3 — Security hygiene is important but doesn't directly address "AI agents getting lost in codebases"
  • Breaking: No — Lock file updates only, no API changes
  • Tier: 1 (zero-dep ✓ + foundation-aligned ✓)

Review Summary

PASSED — Configuration & Test Integrity

  • No configuration changes detected (no biome.json, tsconfig.json, or test modifications)
  • No test changes — test integrity preserved
  • Proper scope — Only 2 files changed: audit report + lock file

PASSED — Security Verification

Vulnerabilities Properly Fixed:

Package Before After Status
hono ≤4.12.6 4.12.9 ✅ Fixed
@hono/node-server <1.19.10 1.19.11 ✅ Fixed
express-rate-limit 8.2.0-8.2.1 8.2.2+ ✅ Fixed
minimatch <3.1.4 3.1.4+ ✅ Fixed
tar ≤7.5.10 >7.5.10 ✅ Fixed

Audit Trail: Comprehensive report in generated/deps-audit/DEPS_AUDIT_2026-03-24.md documents all CVEs with GHSA links and CVSS scores.

PASSED — Dependency Analysis

  • 3 of 5 vulnerabilities traced to @modelcontextprotocol/sdk (optional dependency)
  • No direct dependency changes in package.json
  • Health score improvement: 41/100 → expect 91/100 post-fix (per audit report calculations)
  • Bonus improvements: Biome 2.4.7→2.4.8, Vitest 4.1.0→4.1.1 (safe patch updates)

Minor Observations

  • TypeScript remains at 5.9.3 vs latest 6.0.2 (correctly flagged as stale major — requires evaluation)
  • Report shows excellent dependency hygiene: 0 unused deps, 0 license risks, 0 actionable duplicates

Final Recommendation

  • Rating: ⭐⭐⭐⭐ (4/5)
  • Action: APPROVE
  • Reasoning: Textbook security maintenance — legitimate vulnerability fixes via standard tooling with proper documentation. No configuration shortcuts or test weakening detected. Only loses 1 star for being maintenance rather than feature work.

Excellent work on security hygiene! This PR demonstrates proper vulnerability management with comprehensive audit trails.


@greptile-apps
Copy link
Copy Markdown
Contributor

greptile-apps bot commented Mar 24, 2026

Greptile Summary

This PR resolves all 5 high-severity (and 3 moderate-severity) transitive vulnerabilities via npm audit fix, patches three aging dev dependencies (@biomejs/biome, vitest, @vitest/coverage-v8), and adds a comprehensive pre/post-fix dependency audit report. Only package-lock.json and the new audit report file are changed — package.json is untouched.

Key changes:

  • Security fixes: @hono/node-server 1.19.9→1.19.11, hono 4.12.0→4.12.9, express-rate-limit 8.2.1→8.3.1, minimatch 3.1.3→3.1.5, tar 7.5.9→7.5.13
  • Patch bumps: @biomejs/biome 2.4.7→2.4.8, vitest+@vitest/coverage-v8 4.1.0→4.1.1 (pulling in transitive rolldown rc.9→rc.11, oxc-types 0.115→0.122)
  • Audit report: pre-fix snapshot callout, single consistent health score methodology (39/100 pre-fix → 95/100 post-fix), all advisory GHSA IDs and CVSS scores documented, full transitive pull-through paths for all 5 packages
  • All previous review comments have been addressed across commits 5350633, 04d3762, 083e7f7, 4054d65, and 4713fca

Confidence Score: 5/5

  • This PR is safe to merge — it is a pure lock-file security maintenance update with no source code changes and all tests passing.
  • All 5 vulnerable packages are confirmed patched to versions that meet or exceed the minimum fixed versions stated in their advisories. No direct dependencies (package.json) were changed. The author reports 2033 tests passing with only 2 pre-existing EPERM failures unrelated to this PR. The audit report is accurate and all previously flagged review concerns have been fully addressed.
  • No files require special attention.

Important Files Changed

Filename Overview
generated/deps-audit/DEPS_AUDIT_2026-03-24.md New dependency audit report with pre-fix snapshot callout, consistent health scores (39/100 → 95/100), all 5 high + 3 moderate vulnerabilities documented with CVSS scores and full transitive paths. All previously flagged issues resolved.
package-lock.json Lock file updates fix all 5 high-severity vulnerable packages: @hono/node-server 1.19.9→1.19.11, hono 4.12.0→4.12.9, express-rate-limit 8.2.1→8.3.1, minimatch 3.1.3→3.1.5, tar 7.5.9→7.5.13. Dev tool patch bumps (biome 2.4.7→2.4.8, vitest 4.1.0→4.1.1) pull in expected transitive updates (rolldown rc.9→rc.11, oxc-project/types). No direct dependency (package.json) changes.

Flowchart

%%{init: {'theme': 'neutral'}}%%
flowchart TD
    A["npm audit fix + npm update"] --> B["Vulnerability Fixes"]
    A --> C["Patch Bumps"]

    B --> D["@hono/node-server\n1.19.9 → 1.19.11\nvia @modelcontextprotocol/sdk"]
    B --> E["hono\n4.12.0 → 4.12.9\nvia @modelcontextprotocol/sdk"]
    B --> F["express-rate-limit\n8.2.1 → 8.3.1\nvia @modelcontextprotocol/sdk"]
    B --> G["minimatch\n3.1.3 → 3.1.5\nvia commit-and-tag-version → dotgitignore"]
    B --> H["tar\n7.5.9 → 7.5.13\nvia @huggingface/transformers → onnxruntime-node"]

    C --> I["@biomejs/biome\n2.4.7 → 2.4.8"]
    C --> J["vitest\n4.1.0 → 4.1.1"]
    C --> K["@vitest/coverage-v8\n4.1.0 → 4.1.1"]

    D & E & F --> L["5 HIGH + 3 MODERATE\nvulnerabilities resolved"]
    G & H --> L
    I & J & K --> M["3 aging deps resolved\nHealth: 39/100 → 95/100"]
    L --> M
Loading

Reviews (6): Last reviewed commit: "fix: add CVSS scores and transitive path..." | Re-trigger Greptile

Comment on lines +14 to +20
| **Health score** | **47/100** |

## Health Score Calculation

```
Start: 100
- 5 high vulns × -10: -50
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Audit report reflects pre-fix state

The summary table shows "5 high" vulnerabilities (and the "Recommended Actions" section still says to "run npm audit fix"), but this document is committed as part of the PR that applies those fixes. A reader viewing this file in the future will see it documenting an already-resolved problem as if it were still open.

Consider either:

  1. Updating the report to reflect the post-fix state (0 high vulnerabilities, recalculated health score), or
  2. Naming/labelling the file to clearly signal it is a pre-fix snapshot (e.g., DEPS_AUDIT_2026-03-24_pre-fix.md) and adding a header note such as "Note: this report was captured before the fixes in this PR were applied."

As committed, the document is misleading about the current security posture of the repository.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Addressed in 5350633. Added a pre-fix snapshot callout at the top of the report and restructured the summary as a pre-fix/post-fix comparison table.

Comment on lines +22 to +39
- 1 stale dep (TS 6.x) × -5: -5
(moderate vulns are sub-advisories of hono, counted separately)
Subtotal: 100 - 50 - 9 + 6 = 47
(adjusted: hono has 5 advisories but is 1 package — counting 1 high + 2 moderate for hono)
```

**Adjusted calculation (per-package, not per-advisory):**
- 100 base
- 5 packages with high vulns × -10 = -50
- 1 stale dep × -5 = -5
- 2 aging deps × -2 = -4
- **Score: 41/100**

## Security Vulnerabilities

All 5 are **high** severity and all have fixes available via `npm audit fix`.

### 1. `@hono/node-server` < 1.19.10 — HIGH
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Inconsistent health scores within the same document

The summary table on line 20 states a health score of 47/100, but the detailed recalculation block on line 39 concludes 41/100 using a different (per-package) methodology. Both numbers are derived from the same data, yet neither is clearly labelled as the "official" score, and the two calculations contradict each other within the same section.

Pick one approach and remove or clearly demote the other (e.g., "Adjusted score: 41/100 — see calculation below") to avoid ambiguity.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Addressed in 5350633. Removed the conflicting 47/100 calculation. The report now uses a single methodology (per-package) with one score: 41/100 pre-fix, 95/100 post-fix.

@carlos-alm
Copy link
Copy Markdown
Contributor Author

Addressed Greptile's feedback in 5350633:

  1. Pre-fix snapshot labeling: Added a clear callout at the top of the audit report stating it was captured before applying fixes, with a note that the fixes are applied in the same PR.

  2. Conflicting health scores (47/100 vs 41/100): Removed the duplicate calculation. The report now uses only the per-package score (41/100 pre-fix) and adds a post-fix column showing 91/100.

  3. Recommended Actions section: Updated to show completed items as struck-through, with only the remaining TypeScript 6.0 evaluation listed as outstanding.

@carlos-alm
Copy link
Copy Markdown
Contributor Author

@greptileai

Comment on lines +27 to +31
**Post-fix:** All 5 high-severity vulnerabilities and aging patch deps resolved. Only the stale TypeScript major version remains.
- 100 base
- 1 stale dep × -5 = -5
- 2 aging deps resolved (biome, vitest patched) = 0
- **Score: 91/100** (estimated; TypeScript 6.0 evaluation deferred)
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Post-fix health score math doesn't add up

The post-fix calculation shown here is:

  • 100 base
  • 1 stale dep × −5 = −5
  • 2 aging deps resolved = 0

That yields 95/100, but both this line and the summary table on line 16 report 91/100. There are 4 unaccounted points with no stated deduction. Either the formula is missing a penalty (e.g. a moderate-vulnerability deduction), or the score should be updated to 95/100.

Suggested change
**Post-fix:** All 5 high-severity vulnerabilities and aging patch deps resolved. Only the stale TypeScript major version remains.
- 100 base
- 1 stale dep × -5 = -5
- 2 aging deps resolved (biome, vitest patched) = 0
- **Score: 91/100** (estimated; TypeScript 6.0 evaluation deferred)
- **Score: 95/100** (estimated; TypeScript 6.0 evaluation deferred)

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 04d3762. The post-fix health score is now correctly calculated as 95/100 (100 - 5 for the stale TypeScript dep). The summary table and calculation block are consistent.

Comment on lines +10 to +11
| Total dependencies (transitive) | ~850 | ~850 |
| Security vulnerabilities | 5 high, 3 moderate | 0 high, 0 moderate |
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 3 moderate vulnerabilities are unaccounted for in the Security Vulnerabilities section

The summary table records "5 high, 3 moderate" pre-fix and "0 high, 0 moderate" post-fix, but the Security Vulnerabilities section below only details the 5 high-severity advisories. The 3 moderate-severity packages are never named, linked to advisories, or explained.

Consider adding a brief "Moderate Vulnerabilities" subsection (even just package names, advisory IDs, and fix paths) so the report is self-contained and auditable without having to re-run npm audit.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 04d3762. Added a dedicated "Moderate Severity" subsection documenting all 3 moderate advisories in hono (cookie injection GHSA-5pq2-9x2x-5p6w, SSE injection GHSA-p6xx-57qc-3wxr, prototype pollution GHSA-v8w9-8mx6-g223) with CVSS scores, advisory links, and fix path. They were previously listed inline under the hono high-severity entry but are now separated for clarity.

@carlos-alm
Copy link
Copy Markdown
Contributor Author

@greptileai

Comment on lines +12 to +25
| Outdated packages | 1 stale (major), 3 aging (patch) | 1 stale (major), 0 aging |
| Unused dependencies | 0 | 0 |
| License risks | 0 | 0 |
| Duplicates | 0 actionable | 0 actionable |
| **Health score** | **41/100** | **95/100** |

## Health Score Calculation

**Pre-fix (per-package):**
- 100 base
- 5 packages with high vulns × -10 = -50
- 1 stale dep × -5 = -5
- 2 aging deps × -2 = -4
- **Score: 41/100**
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Aging-dep count mismatch between summary table and health-score formula

The summary table on line 12 explicitly records "1 stale (major), 3 aging (patch)" pre-fix, but the health-score block on line 24 deducts for only 2 aging deps × −2 = −4, not 3. The three patch-behind packages listed in the outdated-packages section are @biomejs/biome, vitest, and @vitest/coverage-v8.

If vitest and @vitest/coverage-v8 are intentionally counted as one logical unit (they're released together from the same mono-repo), that reasoning isn't stated anywhere, and the summary table still lists three aging packages. The discrepancy makes the formula hard to follow.

Either:

  • Update line 24 to 3 aging deps × -2 = -6 → pre-fix score becomes 39/100, or
  • Add a parenthetical explaining the grouping: 2 aging deps (vitest + @vitest/coverage-v8 counted together) × -2 = -4

The same clarification would apply to line 30's post-fix note.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 083e7f7. Updated the formula to count all 3 aging packages individually (@biomejs/biome, vitest, @vitest/coverage-v8), changing the deduction from 2 × -2 = -4 to 3 × -2 = -6 and the pre-fix score from 41/100 to 39/100. The summary table, formula, and post-fix note are now consistent.

The summary table listed 3 aging packages but the health score formula
only deducted for 2. Updated to count all 3 (biome, vitest,
@vitest/coverage-v8) individually, changing pre-fix score from 41 to 39.
@carlos-alm
Copy link
Copy Markdown
Contributor Author

@greptileai


## Recommended Actions

**Resolved in this PR:**
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 ~5.9 pin recommendation is unnecessary

package.json already declares "typescript": "^5.9.3", which resolves to >=5.9.3 <6.0.0. TypeScript 6.x cannot be pulled in automatically under that constraint, so the recommendation to "pin ~5.9" adds no additional protection. The tilde notation would only further restrict minor-version bumps (e.g. a hypothetical 5.10.x), which is overly conservative for a dev-only type-checker.

Consider updating the note to reflect that the existing ^5.9.3 constraint is already sufficient to block the TypeScript 6.0 upgrade.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 4054d65. Updated the recommendation to note that the existing \ constraint in \ already blocks TypeScript 6.x (), so no additional pinning is needed. Removed the \ suggestion.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 4054d65. Updated the recommendation to note that the existing ^5.9.3 constraint in package.json already blocks TypeScript 6.x (>=5.9.3 <6.0.0), so no additional pinning is needed. Removed the ~5.9 suggestion.

The report recommended pinning ~5.9 but package.json already uses
^5.9.3 which blocks TypeScript 6.x. Updated the note to reflect
the existing constraint is sufficient.
@carlos-alm
Copy link
Copy Markdown
Contributor Author

@greptileai

Comment on lines +66 to +70
#### 5. `tar` <= 7.5.10 — HIGH (2 advisories)
- [GHSA-qffp-2rhf-9h96](https://github.com/advisories/GHSA-qffp-2rhf-9h96) — Hardlink path traversal via drive-relative linkpath
- [GHSA-9ppj-qmqm-q256](https://github.com/advisories/GHSA-9ppj-qmqm-q256) — Symlink path traversal via drive-relative linkpath
- **Path:** transitive
- **Fix:** Update to > 7.5.10
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 tar section missing CVSS scores

Every other high-severity entry in this section documents CVSS scores explicitly (e.g. @hono/node-server CVSS 7.5, express-rate-limit CVSS 7.5, hono advisories CVSS 8.2 / 7.5, minimatch CVSS 7.5). The tar block lists both advisories without CVSS values, making it harder to compare severity at a glance.

Consider adding the CVSS scores inline, e.g.:

Suggested change
#### 5. `tar` <= 7.5.10 — HIGH (2 advisories)
- [GHSA-qffp-2rhf-9h96](https://github.com/advisories/GHSA-qffp-2rhf-9h96) — Hardlink path traversal via drive-relative linkpath
- [GHSA-9ppj-qmqm-q256](https://github.com/advisories/GHSA-9ppj-qmqm-q256) — Symlink path traversal via drive-relative linkpath
- **Path:** transitive
- **Fix:** Update to > 7.5.10
#### 5. `tar` <= 7.5.10 — HIGH (2 advisories)
- [GHSA-qffp-2rhf-9h96](https://github.com/advisories/GHSA-qffp-2rhf-9h96) — Hardlink path traversal via drive-relative linkpath (CVSS 7.5)
- [GHSA-9ppj-qmqm-q256](https://github.com/advisories/GHSA-9ppj-qmqm-q256) — Symlink path traversal via drive-relative linkpath (CVSS 7.5)
- **Path:** transitive
- **Fix:** Update to > 7.5.10

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 4713fca. Added CVSS 7.5 scores to both tar advisories (GHSA-qffp-2rhf-9h96 and GHSA-9ppj-qmqm-q256), matching the format used by all other high-severity entries in the report.

Comment on lines +63 to +69
- **Path:** transitive
- **Fix:** Update to >= 3.1.4

#### 5. `tar` <= 7.5.10 — HIGH (2 advisories)
- [GHSA-qffp-2rhf-9h96](https://github.com/advisories/GHSA-qffp-2rhf-9h96) — Hardlink path traversal via drive-relative linkpath
- [GHSA-9ppj-qmqm-q256](https://github.com/advisories/GHSA-9ppj-qmqm-q256) — Symlink path traversal via drive-relative linkpath
- **Path:** transitive
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Unspecified transitive path for minimatch and tar

@hono/node-server, express-rate-limit, and hono all identify their pull-through path (via @modelcontextprotocol/sdk), but minimatch (line 63) and tar (line 69) only say transitive. For a self-contained audit report, it is useful to know which direct dependency brings each vulnerable package in, so future readers can target the right upgrade path.

If the path is known (e.g. tar is likely pulled by a build tool, and minimatch by glob/node-glob), documenting it here would make the report fully auditable without needing to re-run npm ls.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 4713fca. Traced both transitive paths via npm ls on the lockfile:

  • minimatch: via commit-and-tag-version -> dotgitignore
  • tar: via @huggingface/transformers -> onnxruntime-node

Both entries now document the full pull-through path, consistent with the other high-severity entries.

@carlos-alm
Copy link
Copy Markdown
Contributor Author

@greptileai

@carlos-alm carlos-alm merged commit 589fe90 into main Mar 24, 2026
15 checks passed
@carlos-alm carlos-alm deleted the fix/deps-audit-security branch March 24, 2026 09:08
@github-actions github-actions bot locked and limited conversation to collaborators Mar 24, 2026
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant