Skip to content

chore(deps): TypeScript 6, libp2p 0.57 (drops the yamux patch), webrtc 0.21 - #44

Merged
dlukt merged 3 commits into
mainfrom
chore/deps-ts6-libp2p-webrtc
Sep 22, 2026
Merged

dlukt merged 3 commits into
mainfrom
chore/deps-ts6-libp2p-webrtc

Conversation

@dlukt

@dlukt dlukt commented Sep 22, 2026

Copy link
Copy Markdown
Owner

Clears every pending major on both sides before the next Dependabot run. Supersedes #41 and #43. Three commits, one per change, so each can be reverted on its own.

Client: TypeScript 5.9 → 6.0 (supersedes #43)

Server: libp2p 0.56 → 0.57, vendored yamux patch removed

  • libp2p-yamux 0.48 dropped yamux 0.12 upstream, so server/patches/libp2p-yamux (CVE-2026-32314) is gone. No source changes.
  • libp2p-identity 0.3 swapped its protobuf library. Verified that the persisted node key decodes to the same PeerId in both directions (rollback-safe), and added a golden-file test.
  • gossipsub 0.50's new default 100-topic subscription cap doesn't affect us: discool uses 2 topics.
  • Cargo.lock holds the wasm-bindgen family and futures-timer (3.0.3) back, because libp2p-swarm 0.48 pins wasm-bindgen-futures = "=0.4.58" for wasm targets. Harmless for the native build; documented next to the libp2p entry.

Server: webrtc 0.17 → 0.21 (supersedes #41)

0.20 is a rewrite as a thin async layer over the sans-I/O rtc crate, so voice_channel.rs is ported:

  • Explicit UDP bind (0.0.0.0:0). 0.21 binds nothing by default and fails to build with no sockets.
  • ICE gathering completion now arrives through an event handler, bounded at 5 s.
  • Cleanup: the peer connection is closed on every start_signaling error path, since dropping it no longer stops its driver task.
  • New end-to-end test: offer → answer → trickled candidates → connected. Mutation-checked against an empty bind list and against apply_answer skipping the answer.

Behaviour change: host candidates are IPv4-only. [::]:0 misbehaves on hosts without a usable IPv6 address, such as Docker's default bridge: it either logs a bind error per join or advertises :: as a candidate. Dual-stack hosts lose IPv6 host candidates; STUN/TURN (srflx/relay) paths are unaffected.

Tests run

  • client: npm run lint (2 pre-existing useOptionalChain warnings), npm run check (0 errors, 274 files), npm test (294 passed), npm run build, npm audit (0 vulnerabilities)
  • server: cargo fmt --check, cargo clippy -- -D warnings, RUST_TEST_THREADS=1 cargo test (403 passed), cargo audit (clean). Also run at the libp2p commit on its own (402 passed).

Not verified

  • A voice call from a real browser. The handshake test plays the browser with webrtc-rs.
  • The Docker image build. The Dockerfile is unchanged; cargo-chef picked up the patch directory implicitly.

Notes

  • No config or database changes.
  • Dependency tree: 602 → 580 crates.

🤖 Generated with Claude Code

dlukt and others added 3 commits September 22, 2026 20:06
TypeScript 7 (the Go port) ships no compiler API: `typescript@7`'s main
export is only `lib/version.cjs`. svelte-check and svelte2tsx are built
on that API, so PR #43 (5.9.3 -> 7.0.2) could never resolve, let alone
run. Grouping typescript with svelte-check did not prevent it, because
Dependabot does not check peer ranges across a group; an ignore rule for
typescript majors does. The dependabot.yml comment that claimed grouping
was enough is corrected.

Alternatives checked before settling on 6:
- oxlint `--type-aware --type-check` (tsgolint on typescript-go) caught
  an error planted in a .ts file but missed both planted in a .svelte
  file (script and markup). Replacing svelte-check with it would
  silently drop type checking for every component.
- svelte-check `--tsgo`, with TS 7 installed as `@typescript/native`
  alongside TS 6 as its maintainers recommend, works on this codebase
  (all planted errors caught, 2.8s vs 6s). It needs two TypeScript
  installs, turns node_modules/.bin/tsc into TS 7 by link order, and is
  exposed to a silent-pass bug (sveltejs/language-tools#2995). Not worth
  ~3s today.

TypeScript 6.0.3 only needed `baseUrl` dropped (deprecated in 6, gone in
7), which makes the `paths` entries `./`-relative. Also takes
@types/node 24.13.6 and runs `biome migrate` for the installed Biome
2.5.14 (schema URL; `recommended: true` -> `preset: "recommended"`).

Verified: lint, check (0 errors, 274 files), 294 tests, build,
npm audit clean.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
libp2p-yamux 0.48 (libp2p 0.57) removed yamux 0.12 support and depends
only on yamux ^0.14 -- the condition patches/libp2p-yamux/README.md set
for deleting the fork that kept the vulnerable 0.12 line
(CVE-2026-32314) out of the build. No source changes were needed.

Checked the behaviour changes the compiler cannot see:
- libp2p-identity 0.3 swapped its protobuf library. The node key is
  persisted with `to_protobuf_encoding`, so a decoding change would boot
  existing instances with a new PeerId, or not at all. A key written by
  0.2.14 loads under 0.3.0 with the same PeerId and re-encodes
  byte-identically, so files written after the upgrade still load on a
  rollback. Pinned with a golden-file test.
- gossipsub 0.50 caps subscriptions at 100 topics by default; discool
  subscribes to 2.

Cargo.lock moves the wasm-bindgen family and futures-timer backwards
(futures-timer 3.0.4 -> 3.0.3): libp2p-swarm 0.48 pins
`wasm-bindgen-futures = "=0.4.58"` for wasm targets, and the lockfile
resolves for every target. Harmless natively -- see the note on the
libp2p entry in Cargo.toml.

Verified at this commit: fmt, clippy -D warnings, 402 tests, cargo
audit clean.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Supersedes #41 (0.20.5). webrtc 0.20 is a rewrite -- a thin async layer
over the sans-I/O `rtc` crate -- so this is a port rather than a bump,
contained to src/webrtc.

Behaviour the old API provided implicitly and the new one does not:
- Sockets: 0.21 binds only the addresses it is given and fails to build
  with none, so every voice join would have errored. Binds the IPv4
  wildcard, which it expands to one socket per usable interface.
  `[::]:0` is deliberately left out: on a host with no usable IPv6
  address (Docker's default bridge) it is bound verbatim, which either
  logs a bind error on every join or advertises `::` as a host
  candidate. Dual-stack hosts lose IPv6 host candidates; srflx and relay
  candidates are unaffected.
- Gathering: `gathering_complete_promise` is gone; completion arrives
  through a PeerConnectionEventHandler. Bounded at 5s so a STUN or TURN
  server that never answers cannot stall a join.
- Cleanup: dropping a connection no longer stops its driver task and
  sockets, so start_signaling closes it on every error path.
- `RtpCodecKind` lives in `rtc`, a private dependency webrtc does not
  re-export. It is built from its W3C kind string rather than adding
  `rtc` as a direct dependency that would have to move in lockstep.

New test drives the browser's flow against VoiceRuntime: server offer, a
second webrtc peer answers before gathering, its candidates trickle
through apply_remote_candidate, DTLS connects. Mutation-checked: it
fails when the bind list is empty, and when apply_answer skips the
answer -- a path no existing test covered.

Dependency tree: 602 -> 580 crates.
Verified: fmt, clippy -D warnings, 403 tests, cargo audit clean.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@chatgpt-codex-connector

Copy link
Copy Markdown

You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard.
To continue using code reviews, you can upgrade your account or add credits to your account and enable them for code reviews in your settings.

@dlukt
dlukt merged commit 7c9de02 into main Sep 22, 2026
2 checks passed
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.

1 participant