Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions config/internal.go
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,16 @@ type Internal struct {
// Addresses.NoAnnounce. Defaults to DefaultDeadListenerCheck. Set to false
// to disable the check entirely.
DeadListenerCheck Flag `json:",omitempty"`
// NonPublicAddrPublishing toggles whether addresses outside globally
// routable ranges (private, CGNAT, link-local, loopback, ULA, reserved
// IPv6 space, and special-use DNS names such as .local) are kept in the
// peerstore self-entry and the signed peer record, and so announced over
// identify and the DHT. Multiaddrs without an IP or DNS component, such
// as /p2p-circuit, are unaffected. When unset, no option is passed to
// go-libp2p and its default applies. Set to false to keep non-public
// addresses off the wire, which is useful when checking what a node
// advertises.
NonPublicAddrPublishing Flag `json:",omitempty"`
}

type InternalBitswap struct {
Expand Down
87 changes: 87 additions & 0 deletions core/addrs_publishing_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
package core

import (
"os"
"path/filepath"
"testing"
"time"

"github.com/ipfs/boxo/filestore"
"github.com/ipfs/boxo/keystore"
"github.com/ipfs/go-datastore"
syncds "github.com/ipfs/go-datastore/sync"
"github.com/ipfs/kubo/config"
"github.com/ipfs/kubo/core/node/libp2p"
"github.com/ipfs/kubo/repo"
"github.com/stretchr/testify/require"
)

// The peerstore self-entry is what feeds the signed peer record, so a node
// listening only on loopback publishes nothing once non-public addresses are
// filtered out. host.Addrs() keeps reporting them either way: the option
// governs what the node announces, not what it listens on.
func TestInternalNonPublicAddrPublishing(t *testing.T) {
for _, tc := range []struct {
name string
flag config.Flag
wantSelfPublished bool
}{
{"unset announces loopback, matching the go-libp2p default", config.Default, true},
{"true announces loopback, as a LAN-only node needs", config.True, true},
{"false keeps loopback out of the published set", config.False, false},
} {
t.Run(tc.name, func(t *testing.T) {
node := buildOnlineLoopbackNode(t, tc.flag)

require.NotEmpty(t, node.PeerHost.Addrs(), "the host still listens on loopback")

published := waitForSelfAddrs(t, node, tc.wantSelfPublished)
if tc.wantSelfPublished {
require.NotEmpty(t, published, "loopback should be published")
} else {
require.Empty(t, published, "loopback should not be published")
}
})
}
}

func buildOnlineLoopbackNode(t *testing.T, flag config.Flag) *IpfsNode {
t.Helper()

ds := syncds.MutexWrap(datastore.NewMapDatastore())
c := config.Config{}
c.Identity = testIdentity
c.Addresses.Swarm = []string{"/ip4/127.0.0.1/tcp/0"}
c.Internal.NonPublicAddrPublishing = flag
c.Bootstrap = []string{}

node, err := NewNode(t.Context(), &BuildCfg{
Repo: &repo.Mock{
C: c,
D: ds,
K: keystore.NewMemKeystore(),
F: filestore.NewFileManager(ds, filepath.Dir(os.TempDir())),
},
Online: true,
Routing: libp2p.NilRouterOption,
})
require.NoError(t, err)
t.Cleanup(func() { node.Close() })
return node
}

// waitForSelfAddrs polls the peerstore self-entry, which the address manager
// fills asynchronously once the host starts listening.
func waitForSelfAddrs(t *testing.T, n *IpfsNode, wantAddrs bool) []string {
t.Helper()

var addrs []string
require.Eventually(t, func() bool {
addrs = nil
for _, a := range n.Peerstore.Addrs(n.Identity) {
addrs = append(addrs, a.String())
}
return (len(addrs) > 0) == wantAddrs
}, 5*time.Second, 50*time.Millisecond)
return addrs
}
1 change: 1 addition & 0 deletions core/node/groups.go
Original file line number Diff line number Diff line change
Expand Up @@ -211,6 +211,7 @@ func LibP2P(bcfg *BuildCfg, cfg *config.Config, userResourceOverrides rcmgr.Part
fx.Provide(libp2p.ListenOn(cfg.Addresses.Swarm)),
fx.Invoke(libp2p.SetupDiscovery(cfg.Discovery.MDNS.Enabled)),
fx.Provide(libp2p.ForceReachability(cfg.Internal.Libp2pForceReachability)),
fx.Provide(libp2p.NonPublicAddrPublishing(cfg.Internal.NonPublicAddrPublishing)),
fx.Provide(libp2p.HolePunching(cfg.Swarm.EnableHolePunching, enableRelayClient)),

fx.Provide(libp2p.Security(!bcfg.DisableEncryptedConnections, cfg.Swarm.Transports)),
Expand Down
13 changes: 13 additions & 0 deletions core/node/libp2p/libp2p.go
Original file line number Diff line number Diff line change
Expand Up @@ -104,3 +104,16 @@ func ForceReachability(val *config.OptionalString) func() (opts Libp2pOpts, err
return
}
}

// NonPublicAddrPublishing controls whether non-globally-routable addresses stay
// in the peerstore self-entry and the signed peer record. Leaving the flag unset
// passes no option, so go-libp2p's own default decides.
func NonPublicAddrPublishing(val config.Flag) func() (opts Libp2pOpts) {
return func() (opts Libp2pOpts) {
if val == config.Default {
return
}
opts.Opts = append(opts.Opts, libp2p.NonPublicAddrPublishing(val == config.True))
return
}
}
25 changes: 25 additions & 0 deletions core/node/libp2p/libp2p_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,37 @@ import (
"strconv"
"testing"

"github.com/ipfs/kubo/config"
"github.com/libp2p/go-libp2p"
ma "github.com/multiformats/go-multiaddr"

"github.com/stretchr/testify/require"
)

func TestNonPublicAddrPublishing(t *testing.T) {
for _, tc := range []struct {
name string
flag config.Flag
wantOptCount int
wantDisabled bool
}{
{"unset defers to go-libp2p", config.Default, 0, false},
{"true announces private addrs, as a LAN-only node needs", config.True, 1, false},
{"false keeps private addrs off identify and the DHT", config.False, 1, true},
} {
t.Run(tc.name, func(t *testing.T) {
opts := NonPublicAddrPublishing(tc.flag)()
require.Len(t, opts.Opts, tc.wantOptCount)

var cfg libp2p.Config
for _, opt := range opts.Opts {
require.NoError(t, opt(&cfg))
}
require.Equal(t, tc.wantDisabled, cfg.DisableNonPublicAddrPublishing)
})
}
}

func TestPrioritize(t *testing.T) {
// The option is encoded into the port number of a TCP multiaddr.
// By extracting the port numbers obtained from the applied option, we can make sure that
Expand Down
39 changes: 39 additions & 0 deletions docs/changelogs/v0.43.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,10 @@ This release was brought to you by the [Shipyard](https://ipshipyard.com/) team.
- [🔑 `ipfs config replace` keeps PeerID and private key in sync](#-ipfs-config-replace-keeps-peerid-and-private-key-in-sync)
- [🔐 secp256k1 key generation, export, and import](#-secp256k1-key-generation-export-and-import)
- [🔄 Sturdier DHT reprovides on large nodes](#-sturdier-dht-reprovides-on-large-nodes)
- [📡 Future-proofing `webrtc-direct` with v2 support](#-future-proofing-webrtc-direct-with-v2-support)
- [🗺️ Fewer stale addresses in the peerstore](#-fewer-stale-addresses-in-the-peerstore)
- [🏁 `ipfs routing findprovs` no longer crashes the daemon](#-ipfs-routing-findprovs-no-longer-crashes-the-daemon)
- [🛡️ Memory exhaustion fix for pubsub](#-memory-exhaustion-fix-for-pubsub)
- [📊 Telemetry is now opt-in](#-telemetry-is-now-opt-in)
- [📦️ Dependency updates](#-dependency-updates)
- [📝 Changelog](#-changelog)
Expand Down Expand Up @@ -88,12 +92,47 @@ ed25519 and secp256k1 keys are always 256 bits, so `--size` (`--bits` for `ipfs
#### 🔄 Sturdier DHT reprovides on large nodes

[go-libp2p-kad-dht v0.41.0](https://github.com/libp2p/go-libp2p-kad-dht/releases/tag/v0.41.0) lowers peak memory during reprovides on nodes that announce many CIDs, so low-memory consumer devices are less likely to be out-of-memory killed. More in [kad-dht#1259](https://github.com/libp2p/go-libp2p-kad-dht/pull/1259).

#### 📡 Future-proofing `webrtc-direct` with v2 support

Kubo listens on `/webrtc-direct` by default, the transport that lets a browser dial your node with no signalling server and no CA-issued certificate. Google Chrome [plans](https://issues.webrtc.org/issues/411871813) to remove the browser behavior that transport's original handshake relies on. Kubo now also accepts the replacement [(v2) handshake](https://github.com/libp2p/specs/pull/715), so your node is ready before that change reaches browsers. Nothing to do today, and old clients keep working. More in [go-libp2p#3520](https://github.com/libp2p/go-libp2p/pull/3520), and [libp2p/specs#672](https://github.com/libp2p/specs/issues/672#issuecomment-4297060067) tracks progress across the other libp2p implementations.

Two more `webrtc-direct` fixes ship in the same bump:

- Your node's `/certhash` address now survives a restart. It used to change on every start, so every cached copy of your address, in other peers' address books and in DHT records, went stale. More in [go-libp2p#3512](https://github.com/libp2p/go-libp2p/pull/3512).
- A peer flooding your node can no longer make a single `webrtc-direct` connection track an unbounded number of addresses. More in [go-libp2p#3500](https://github.com/libp2p/go-libp2p/pull/3500).

#### 🗺️ Fewer stale addresses in the peerstore

Your node remembers addresses for peers it hears about, and dead ones pile up and waste dial attempts. Three fixes trim them:

- Addresses for a peer you are not connected to are capped at 64, dropping the one closest to expiry first. A misbehaving peer can no longer bury good addresses under hundreds of stale ones. More in [go-libp2p#3486](https://github.com/libp2p/go-libp2p/pull/3486).
- When a peer announces a newer signed address list, it now replaces the stored one instead of merging into it. Addresses in use by a live connection are kept. More in [go-libp2p#3487](https://github.com/libp2p/go-libp2p/pull/3487).
- Kubo no longer puts empty addresses into the signed records it announces about itself, which other implementations error out on. More in [go-libp2p#3494](https://github.com/libp2p/go-libp2p/pull/3494).

The new [`Internal.NonPublicAddrPublishing`](https://github.com/ipfs/kubo/blob/master/docs/config.md#internalnonpublicaddrpublishing) flag controls whether your node publishes addresses the wider internet cannot reach, such as private, CGNAT, and loopback ranges. Set it to `false` to keep them out of the signed peer record and the DHT, or `true` to publish them, which is what a LAN-only node wants. Leave it unset to follow go-libp2p's defaults, which [are known to change](https://github.com/libp2p/go-libp2p/issues/3460).

#### 🏁 `ipfs routing findprovs` no longer crashes the daemon

A data race could corrupt the results streamed by `ipfs routing findprovs`, `ipfs routing findpeer`, and `ipfs dht query`, taking the whole daemon down mid-response. More in [go-libp2p#3490](https://github.com/libp2p/go-libp2p/pull/3490).

#### 🛡️ Memory exhaustion fix for pubsub

If you turned pubsub on, update to this release. A remote peer could subscribe to an endless stream of unique topic names, disconnect, and leave your node holding every one of them. Memory grew with each round and never came back until a restart. Kubo now frees a topic's state once the last peer leaves it, and limits how much a peer can pack into a single control message.

This flaw is already public, which is why we name it here. libp2p disclosed it against js-libp2p as [GHSA-4f8r-922h-2vgv](https://github.com/advisories/GHSA-4f8r-922h-2vgv) (CVE-2026-46679), and the Go and Python implementations track the same pattern in open issues, [go-libp2p-pubsub#705](https://github.com/libp2p/go-libp2p-pubsub/issues/705) and [py-libp2p#1349](https://github.com/libp2p/py-libp2p/issues/1349).

> [!IMPORTANT]
> Default configurations are unaffected, because pubsub stays off unless you opt in. It starts if you enable either [`Pubsub.Enabled`](https://github.com/ipfs/kubo/blob/master/docs/config.md#pubsubenabled) or [`Ipns.UsePubsub`](https://github.com/ipfs/kubo/blob/master/docs/config.md#ipnsusepubsub), so if you set either one, update as soon as you can.

#### 📊 Telemetry is now opt-in

The telemetry plugin is now opt-in and ships with no built-in endpoint: a node sends nothing until you set `Plugins.Plugins.telemetry.Config.Mode` to `on` and `Endpoint` to a collector you run, documented along with the payload schema in [telemetry.md](https://github.com/ipfs/kubo/blob/master/docs/telemetry.md).

#### 📦️ Dependency updates

- update `go-libp2p` to a pre-release pinned at [95be6665](https://github.com/libp2p/go-libp2p/commit/95be6665b014e3e29bdb639ec10f8944d141969d), ahead of v0.48.0 (no tagged release yet)
- update `go-libp2p-pubsub` to a pre-release pinned at [01917ab4](https://github.com/libp2p/go-libp2p-pubsub/commit/01917ab4bc72511f5d13395445560e2575a51e44), ahead of v0.16.0 (no tagged release yet), for the pubsub memory exhaustion fix above
- update `go-libp2p-kad-dht` to [v0.41.0](https://github.com/libp2p/go-libp2p-kad-dht/releases/tag/v0.41.0)
- update `p2p-forge/client` to [v0.9.1](https://github.com/ipshipyard/p2p-forge/releases/tag/v0.9.1) (incl. [v0.9.0](https://github.com/ipshipyard/p2p-forge/releases/tag/v0.9.0), [v0.8.1](https://github.com/ipshipyard/p2p-forge/releases/tag/v0.8.1))
- update `go-ds-pebble` to [v0.5.12](https://github.com/ipfs/go-ds-pebble/releases/tag/v0.5.12)
Expand Down
15 changes: 15 additions & 0 deletions docs/config.md
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,7 @@ config file at runtime.
- [`Internal.ShutdownTimeout`](#internalshutdowntimeout)
- [`Internal.CGNATCheck`](#internalcgnatcheck)
- [`Internal.DeadListenerCheck`](#internaldeadlistenercheck)
- [`Internal.NonPublicAddrPublishing`](#internalnonpublicaddrpublishing)
- [`Ipns`](#ipns)
- [`Ipns.RepublishPeriod`](#ipnsrepublishperiod)
- [`Ipns.RecordLifetime`](#ipnsrecordlifetime)
Expand Down Expand Up @@ -1991,6 +1992,20 @@ Default: `true`

Type: `flag`

### `Internal.NonPublicAddrPublishing`

Controls whether the node publishes addresses that are not globally reachable: private-network ranges, carrier-grade NAT (`100.64.0.0/10`), link-local, loopback, unique local addresses, reserved IPv6 space, and special-use DNS names such as `.local`. Such addresses are useless to peers on the wider internet, and they say a little about your internal network.

Set to `false` to keep them out of the peerstore self-entry and the signed peer record, so they stay out of DHT records and out of the signed record peers receive over identify. Useful when you want to pin down exactly what a node publishes, for example while reproducing a routing problem. Set it to `true` to publish them, which is what a LAN-only or test node wants.

A few limits worth knowing. Addresses without an IP or DNS component, such as `/p2p-circuit`, are never filtered. The setting changes only what the node publishes, never what it listens on or dials, so [`ipfs id`](https://docs.ipfs.tech/reference/kubo/cli/#ipfs-id) and [`ipfs swarm addrs local`](https://docs.ipfs.tech/reference/kubo/cli/#ipfs-swarm-addrs-local) still report the unfiltered set. Peers reading the signed peer record see the filtered addresses; the older unsigned address list that identify also carries is untouched.

When left unset, Kubo passes no option and the go-libp2p default applies.

Default: unset (go-libp2p default)

Type: `flag`

## `Ipns`

### `Ipns.RepublishPeriod`
Expand Down
4 changes: 2 additions & 2 deletions docs/examples/kubo-as-a-library/go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ replace github.com/ipfs/kubo => ./../../..
require (
github.com/ipfs/boxo v0.41.1-0.20260707130650-177b35c8ef09
github.com/ipfs/kubo v0.0.0-00010101000000-000000000000
github.com/libp2p/go-libp2p v0.48.0
github.com/libp2p/go-libp2p v0.48.1-0.20260708062241-95be6665b014
github.com/multiformats/go-multiaddr v0.16.1
)

Expand Down Expand Up @@ -120,7 +120,7 @@ require (
github.com/libp2p/go-libp2p-asn-util v0.4.1 // indirect
github.com/libp2p/go-libp2p-kad-dht v0.41.0 // indirect
github.com/libp2p/go-libp2p-kbucket v0.8.0 // indirect
github.com/libp2p/go-libp2p-pubsub v0.16.0 // indirect
github.com/libp2p/go-libp2p-pubsub v0.16.1-0.20260707102207-01917ab4bc72 // indirect
github.com/libp2p/go-libp2p-pubsub-router v0.6.0 // indirect
github.com/libp2p/go-libp2p-record v0.3.1 // indirect
github.com/libp2p/go-libp2p-routing-helpers v0.7.5 // indirect
Expand Down
12 changes: 6 additions & 6 deletions docs/examples/kubo-as-a-library/go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -411,8 +411,8 @@ github.com/libp2p/go-flow-metrics v0.0.1/go.mod h1:Iv1GH0sG8DtYN3SVJ2eG221wMiNpZ
github.com/libp2p/go-flow-metrics v0.0.3/go.mod h1:HeoSNUrOJVK1jEpDqVEiUOIXqhbnS27omG0uWU5slZs=
github.com/libp2p/go-flow-metrics v0.3.0 h1:q31zcHUvHnwDO0SHaukewPYgwOBSxtt830uJtUx6784=
github.com/libp2p/go-flow-metrics v0.3.0/go.mod h1:nuhlreIwEguM1IvHAew3ij7A8BMlyHQJ279ao24eZZo=
github.com/libp2p/go-libp2p v0.48.0 h1:h2BrLAgrj7X8bEN05K7qmrjpNHYA+6tnsGRdprjTnvo=
github.com/libp2p/go-libp2p v0.48.0/go.mod h1:Q1fBZNdmC2Hf82husCTfkKJVfHm2we5zk+NWmOGEmWk=
github.com/libp2p/go-libp2p v0.48.1-0.20260708062241-95be6665b014 h1:RYkdiaWH3aPT7m98atoCw+MD2YJOHfUi16ZaXaP3yGg=
github.com/libp2p/go-libp2p v0.48.1-0.20260708062241-95be6665b014/go.mod h1:+zGTonNiePk+PlraDn51k+8grAbHh9df7IIAVOMwqZo=
github.com/libp2p/go-libp2p-asn-util v0.4.1 h1:xqL7++IKD9TBFMgnLPZR6/6iYhawHKHl950SO9L6n94=
github.com/libp2p/go-libp2p-asn-util v0.4.1/go.mod h1:d/NI6XZ9qxw67b4e+NgpQexCIiFYJjErASrYW4PFDN8=
github.com/libp2p/go-libp2p-core v0.2.4/go.mod h1:STh4fdfa5vDYr0/SzYYeqnt+E6KfEV5VxfIrm0bcI0g=
Expand All @@ -423,8 +423,8 @@ github.com/libp2p/go-libp2p-kbucket v0.3.1/go.mod h1:oyjT5O7tS9CQurok++ERgc46YLw
github.com/libp2p/go-libp2p-kbucket v0.8.0 h1:QAK7RzKJpYe+EuSEATAaaHYMYLkPDGC18m9jxPLnU8s=
github.com/libp2p/go-libp2p-kbucket v0.8.0/go.mod h1:JMlxqcEyKwO6ox716eyC0hmiduSWZZl6JY93mGaaqc4=
github.com/libp2p/go-libp2p-peerstore v0.1.4/go.mod h1:+4BDbDiiKf4PzpANZDAT+knVdLxvqh7hXOujessqdzs=
github.com/libp2p/go-libp2p-pubsub v0.16.0 h1:j7G2C8kJwkcAQqYR7Wmq3d75d3Sgw/N0Hhiv0dVx7OY=
github.com/libp2p/go-libp2p-pubsub v0.16.0/go.mod h1:lr4oE8bFgQaifRcoc2uWhWWiK6tPdOEKpUuR408GFN4=
github.com/libp2p/go-libp2p-pubsub v0.16.1-0.20260707102207-01917ab4bc72 h1:+FxFDSXkULD3f7qL0iSzvJLpMcsDd315HVdA3sY7nsk=
github.com/libp2p/go-libp2p-pubsub v0.16.1-0.20260707102207-01917ab4bc72/go.mod h1:F0oKCGLFJNy9b0TyRi04b+LchEzq0t2eZyJuxwAIyDE=
github.com/libp2p/go-libp2p-pubsub-router v0.6.0 h1:D30iKdlqDt5ZmLEYhHELCMRj8b4sFAqrUcshIUvVP/s=
github.com/libp2p/go-libp2p-pubsub-router v0.6.0/go.mod h1:FY/q0/RBTKsLA7l4vqC2cbRbOvyDotg8PJQ7j8FDudE=
github.com/libp2p/go-libp2p-record v0.3.1 h1:cly48Xi5GjNw5Wq+7gmjfBiG9HCzQVkiZOUZ8kUl+Fg=
Expand All @@ -450,8 +450,8 @@ github.com/libp2p/zeroconf/v2 v2.2.0 h1:Cup06Jv6u81HLhIj1KasuNM/RHHrJ8T7wOTS4+Tv
github.com/libp2p/zeroconf/v2 v2.2.0/go.mod h1:fuJqLnUwZTshS3U/bMRJ3+ow/v9oid1n0DmyYyNO1Xs=
github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ=
github.com/mailru/easyjson v0.0.0-20180823135443-60711f1a8329/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
github.com/marcopolo/simnet v0.0.4 h1:50Kx4hS9kFGSRIbrt9xUS3NJX33EyPqHVmpXvaKLqrY=
github.com/marcopolo/simnet v0.0.4/go.mod h1:tfQF1u2DmaB6WHODMtQaLtClEf3a296CKQLq5gAsIS0=
github.com/marcopolo/simnet v0.0.7 h1:DpH8BMGsF9+1w13L8rvCaAhb6nYJdY+dIXncDrssvUs=
github.com/marcopolo/simnet v0.0.7/go.mod h1:tfQF1u2DmaB6WHODMtQaLtClEf3a296CKQLq5gAsIS0=
github.com/marten-seemann/tcp v0.0.0-20210406111302-dfbc87cc63fd h1:br0buuQ854V8u83wA0rVZ8ttrq5CpaPZdvrK0LP2lOk=
github.com/marten-seemann/tcp v0.0.0-20210406111302-dfbc87cc63fd/go.mod h1:QuCEs1Nt24+FYQEqAAncTDPJIuGs+LxK1MCiFL25pMU=
github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU=
Expand Down
4 changes: 2 additions & 2 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -51,11 +51,11 @@ require (
github.com/jbenet/go-temp-err-catcher v0.1.0
github.com/julienschmidt/httprouter v1.3.0
github.com/libp2p/go-doh-resolver v0.5.0
github.com/libp2p/go-libp2p v0.48.0
github.com/libp2p/go-libp2p v0.48.1-0.20260708062241-95be6665b014 // TODO: switch to a tagged release once one ships past v0.48.0
github.com/libp2p/go-libp2p-http v0.5.0
github.com/libp2p/go-libp2p-kad-dht v0.41.0
github.com/libp2p/go-libp2p-kbucket v0.8.0
github.com/libp2p/go-libp2p-pubsub v0.16.0
github.com/libp2p/go-libp2p-pubsub v0.16.1-0.20260707102207-01917ab4bc72 // TODO: switch to a tagged release once one ships past v0.16.0
github.com/libp2p/go-libp2p-pubsub-router v0.6.0
github.com/libp2p/go-libp2p-record v0.3.1
github.com/libp2p/go-libp2p-routing-helpers v0.7.5
Expand Down
Loading
Loading