Download Latest Version v2.2.2 source code.zip (1.2 MB)
Email in envelope

Get an email when there's a new version of libp2p

Home / v2.3.0
Name Modified Size InfoDownloads / Week
Parent folder
README.md 2026-08-24 19.7 kB
v2.3.0 source code.tar.gz 2026-08-24 1.0 MB
v2.3.0 source code.zip 2026-08-24 1.3 MB
Totals: 3 Items   2.4 MB 0

Highlights

  • The C bindings were rebuilt around generated nim-ffi bindings, replacing the legacy hand-written implementation while restoring API coverage for connectivity, streams, custom protocols, GossipSub, Kademlia, service discovery, relay, peerstore, crypto, and metrics.
  • QUIC performance was significantly improved by upgrading to nim-lsquic v0.8.0, with more efficient socket draining and engine scheduling, lower-copy receive/write paths, faster packet routing, and more reliable settlement of pending stream operations during connection close.
  • Android and iOS build targets were added for the C bindings, including device and simulator architectures and tests on Android and iOS simulators.
  • Kademlia received substantial interoperability and performance improvements: larger protocol-compatible message limits, 48-hour provider records, liveness-gated routing-table admission and eviction, continuous alpha-concurrency lookups, beta convergence, optimistic provider announcements, and dynamic client/server mode driven by network reachability.
  • Service Discovery gained automatic bootstrapping for per-service routing tables, safer shutdown and concurrency handling, IPv6-aware peer scoring, routing-table admission checks, registrar-cache improvements, and support for advertising a caller-provided signed Extended Peer Record.
  • Protocol interoperability was tightened across the stack: routing records now use the specified proto3 encoding, yamux uses the standard 256 KiB window and rejects invalid versions, QUIC validates the expected peer ID during the TLS handshake, and DCUtR preserves the QUIC server role during hole punching.
  • NAT port mapping now uses nim-libplum, providing automatic PCP, NAT-PMP, and UPnP-IGD selection with simpler lifecycle and build integration.
  • PubSub protobuf messages now use protobuf Editions. Common Message and control-message fields are plain Nim values again, while fields whose wire presence is meaningful remain Opt[T].
  • GossipSub ingress controls are exposed through the C bindings, including maximum message size, per-peer protocol-overhead rate limits, and optional disconnection of peers that exceed those limits.
  • Runtime log filtering can now be configured before C-binding node construction, avoiding unwanted startup logs.
  • Dependency setup was simplified around Nimble’s resolver: contributors can now use make followed by make test, while lockfiles remain for application-like artifacts such as C bindings and Nix builds.

Breaking changes

  • The legacy hand-written C bindings were replaced by nim-ffi generated bindings. C consumers must regenerate c_bindings/libp2p.h, rebuild against the new ABI, and adapt their context calls and result callbacks. The old cbind/libp2p.h and legacy threaded implementation were removed.
  • Additional C ABI changes include:
  • transport, muxer, and peer direction now use generated enums instead of integer literals.
  • libp2p_ctx_create_cid and libp2p_ctx_decode_xpr became libp2p_static_create_cid and libp2p_static_decode_xpr and no longer require a context.
  • libp2p_ctx_destroy now returns an integer status.
  • Raw callbacks may receive the non-terminal RET_STALE_WARN status while a long-running request remains in flight.
  • Libp2pConfig now contains a nested gossipsub configuration. mountGossipsub and gossipsubTriggerSelf moved to gossipsub.mount and gossipsub.triggerSelf.
  • Relay v1 HOP is no longer advertised by the default Relay.new(). Applications that still need the legacy protocol must explicitly use Relay.new(circuitRelayV1 = true). Relay v2 remains enabled by default.
  • IdentifyPusher is disabled by default. Applications that rely on Identify Push announcements must opt in with SwitchBuilder.new().withIdentifyPusher().
  • KadDHT.new(..., client: bool) became KadDHT.new(..., isServer: bool = true). Note the inverted meaning: the old client = true is equivalent to isServer = false. Switch-builder users can instead select KadMode.Client, KadMode.Server, or KadMode.Auto.
  • AutoNAT v1’s AutonatMsg.msgType and AutonatDialResponse.status are now Opt[T]. Code that directly constructs or reads those protobuf structures must wrap or unwrap the values.
  • NAT port-mapping configuration changed with the move to nim-libplum:
  • upnpConfig() and natPmpConfig() no longer accept refreshInterval or leaseDuration; they accept discoveryTimeout and mappingTimeout.
  • natConfig() is the recommended default and automatically tries PCP, NAT-PMP, and UPnP-IGD.
  • DefaultRefreshInterval and DefaultLeaseDuration were removed.
  • Custom PortMapper implementations must remove discover; map no longer accepts a lease and now returns a MappedPort.
  • Outbound dialing and identification now have bounded deadlines, dial locks are cleaned up safely, and inbound connection rejection no longer stalls the accept loop or causes unbounded cleanup work.
  • Kademlia now reuses per-peer RPC streams, enforces per-bucket IP diversity, backs off failed admission probes, automatically re-seeds undersized routing tables, and preserves peer addresses when admission-probe capacity is exhausted.

What's Changed

New Contributors

Full Changelog: https://github.com/vacp2p/nim-libp2p/compare/v2.2.0...v2.3.0

Source: README.md, updated 2026-08-24