Skip to content

fix(deps): bump PyJWT to 2.13.0, fixing CVE-2026-48526 HMAC key-confusion auth bypass - #2058

Open
AmirF194 wants to merge 2 commits into
oraios:mainfrom
AmirF194:fix/1934-pyjwt-hmac-cve-pin-bump
Open

AmirF194 wants to merge 2 commits into
oraios:mainfrom
AmirF194:fix/1934-pyjwt-hmac-cve-pin-bump

Conversation

@AmirF194

Copy link
Copy Markdown
Contributor

One of the vulnerabilities asked about in #1934: pyproject.toml's dev-extra security-pin block still pins PyJWT==2.12.0, which carries CVE-2026-48526 (GHSA-xgmm-8j9v-c9wx). The verifier doesn't check the JWK's declared use, so an issuer's RSA/EC public key can be replayed as an HMAC secret to forge tokens on any code path that accepts both algorithm families. Fixed upstream in 2.13.0.

Bumped the pin and regenerated uv.lock (uv lock --upgrade-package pyjwt); the rest of the lockfile diff is the resolver's own marker simplification from the version bump, not a hand edit (a pristine re-lock reproduces it exactly).

Scoped to PyJWT only. The other two findings from the same scan aren't in this PR: tornado's CVE-2026-82397 already has an open PR (#1964), and there's a separate one this scan turned up that isn't, gitpython 3.1.58's CVE-2026-78676 (CRITICAL RCE), pulled in transitively through the optional agno extra with no existing pin to bump. Left it out to keep this PR to one dependency; happy to open a follow-up if that's useful.

Verified on Python 3.11 and 3.14 (the declared range's extremes): uv sync --extra dev --locked passes on both, uv run serena project health-check still passes end to end, and a trivy scan of the regenerated lockfile shows the PyJWT finding gone.

Refs #1934, not closing it: tornado and gitpython are still open.

…sion auth bypass

Dependabot-flagged transitive dev dependency, pinned in pyproject.toml's
security-pin block for exactly this reason. Same remedy shape as the
maintainer's own prior pin bumps in this block (e.g. 823d5bb).

@feiiiiii5 feiiiiii5 left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Reviewed the diff and the resolved lockfile at the current head. The bump itself checks out; one framing point is worth correcting because it changes how this gets triaged.

Advisory. GHSA-xgmm-8j9v-c9wx = CVE-2026-48526, published 2026-06-15, high, CVSS 7.4, summary "PyJWT: Public-key JWK accepted as HMAC secret enables forged HS256 tokens when mixed families are allowed", affected range pyjwt < 2.13.0, first patched 2.13.0. So 2.13.0 is the right target and the title's characterisation matches the advisory.

Reach is wider than "dev-extra". PyJWT==2.13.0 does sit in [project.optional-dependencies].dev (pyproject.toml:95), and serena-agent's own requirement line in the lock carries marker = "extra == 'dev'" (uv.lock:2870). But serena's core dependency mcp==1.28.1 (pyproject.toml:24) requires pyjwt[crypto] (uv.lock:1365), and uv.lock pins a single version per package — so the dev-extra pin is exactly what fixed 2.12.0 into the resolved set that a plain uv sync installs, which is also the path #1934 ("CVEs in docker image") cares about. Suggest the CHANGELOG line say that; "dev-extra security-pin block" reads as contributor-only and undersells the reason to take it.

Nothing else moved, which is the part a reviewer needs. Of the 78 changed lines in uv.lock, 8 are PyJWT (the requirement specifier, the package version, and the sdist/wheel hash pairs). No other version = line and no other hash changes anywhere in the diff. The rest drop redundant python_full_version < '3.12' / < '3.13' prefixes inside the clr-loader and ipython dependency blocks — consistent with your "resolver marker simplification, not a hand edit".

Exposure inside serena is nil. A code search for jwt in this repo returns pyproject.toml alone, so nothing in serena verifies an HS256 token against a JWK. The case for merging is the resolved lock version (and the image), not an active use path.

Could not verify, so not asserting it. I was unable to confirm the two identifiers you mention in passing — tornado CVE-2026-82397 and gitpython CVE-2026-78676 — through the advisory endpoints available to me: GET /advisories?cve=… ignores the parameter and returns an unfiltered list, and OSV lookups for those ids return 404. Neither is a question for this PR since nothing here changes them, and #1964 does resolve as described (open, dependabot). A GHSA permalink for the gitpython one would help whoever picks it up, since "CRITICAL RCE" is a strong claim to leave unlinked in an issue thread.

No request beyond the CHANGELOG wording; the dependency change looks correct and minimal.

The pyjwt pin also fixes the version uv.lock resolves for mcp's own
pyjwt[crypto] requirement, not only the dev-extra block; a reviewer
flagged the prior wording as underselling why this is worth taking.
@AmirF194

Copy link
Copy Markdown
Contributor Author

Good catch on the framing. Pushed a CHANGELOG wording fix: the pin also fixes
the version uv.lock resolves for mcp's own pyjwt[crypto] requirement,
since uv.lock only carries one version per package. Left the CVE numbers
alone since neither is touched by this diff, same as you found.

@feiiiiii5

Copy link
Copy Markdown

Confirmed against the new head: the wording is now exactly what the lock says. uv.lock:1365 lists
mcp's requirement as { name = "pyjwt", extra = ["crypto"] } with no specifier field, and the only
pyjwt specifier anywhere in the lock is uv.lock:2870 — serena-agent's marker = "extra == 'dev'",
==2.13.0. So "the pin also fixes the version mcp resolves to, because mcp requires pyjwt[crypto]
with no version of its own" is precise, and a reader can verify it in those two lines.

Nothing further from me. For what it is worth to whoever merges: apart from the eight pyjwt lines
(Requirement specifier, package version, sdist + wheel hash pairs) no other version = or hash line
changes in this diff, so the remaining lock churn is marker metadata only.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants