* Initial pass at Telemetry plugin Currently, IP Shipyard, with the help of Probelab, monitor and extract Amino/IPFS public network metrics with the use of DHT crawlers and bootstrappers (via peerlog plugin). For example, we log all peer IDs seen and their AgentVersion/Addresses obtained from the `identify` protocol, which provides insights into protocol usage, total number of peers etc. We would like to increase the ability to obtain more insights from the network by collecting some more information in the future, but also to give users more control over this collection (i.e. opt-out). The information collected will not allow unique identification of anyone and is only used for aggregation. Now, this PR explores a way of moving in this direction: * A new "telemetry" fx plugin is in charge of dealing with telemetry * The FX plugin allows to plug and make decisions / take actions during the setup phase: * We can inspect whether we are using Private Networks before the libp2p.Host has been initialized. * We can send telemetry after the libp2p Host is initialized. * Everything is self-contained. Custom builds can remove the plugin altogether without needing to surgically edit the code. As for behaviour: * The user can opt-in/out via EnvVar, file in the repo path or plugin configuration. * Users on private networks or with custom bootstrappers are detected, offered a wall of text explaining why we need telemetry and invited to opt-in. Opt-out happens otherwise on a timeout (with no input). Their preferences are stored. * Users on standard settings are opted-in by default. This is the status quo in Kubo already, except they don't get a chance to opt out. The telemetry libp2p protocol is yet to be defined, but expect something similar to identify, with a protobuf being pushed to bootstrappers or to a specific telemetry node that we define. In the case of pnets, this will be done with a temporary peer. * checkpoint * telemetry plugin: second pass * On first run it generates a UUID and shows a message to the user. * UUID is persistend to "telemetry_uuid" * Sends telemetry 1 minute after boot and every 24h * LogEvent is the thing containing all the telemetry that is sent * Opt-out possible via env-var or plugin configuration * Telemetry: add changelog and environment variable documentation * docs: improved daemon message making it more obvious nothing was sent yet and that user had 15m to out-out plus some debug logs that confirm opt-out * refactor: rename IPFS_TELEMETRY_MODE to IPFS_TELEMETRY * fix: add User-Agent header to telemetry requests --------- Co-authored-by: Andrew Gillis <11790789+gammazero@users.noreply.github.com> Co-authored-by: Marcin Rataj <lidel@lidel.org>
11 KiB
Kubo changelog v0.37
This release was brought to you by the Shipyard team.
v0.37.0
- Overview
- 🔦 Highlights
- 🚦 Gateway concurrent request limits and retrieval timeouts
- Clear provide queue when reprovide strategy changes
- 🪵 Revamped
ipfs log levelcommand - 📌 Named pins in
ipfs addcommand - Custom sequence numbers in
ipfs name publish - ⚙️
Reprovider.Strategyis now consistently respected - Removed unnecessary dependencies
- Improved
ipfs cid - Deprecated
ipfs stats reprovide - 🔄 AutoRelay now uses all connected peers for relay discovery
- 📊 Anonymous telemetry for better feature prioritization
- 📦️ Important dependency updates
- 📝 Changelog
- 👨👩👧👦 Contributors
Overview
🔦 Highlights
🚦 Gateway concurrent request limits and retrieval timeouts
New configurable limits protect gateway resources during high load:
Gateway.RetrievalTimeout(default: 30s): Maximum duration for content retrieval. Returns 504 Gateway Timeout when exceeded - applies to both initial retrieval (time to first byte) and between subsequent writes.Gateway.MaxConcurrentRequests(default: 4096): Limits concurrent HTTP requests. Returns 429 Too Many Requests when exceeded. Protects nodes from traffic spikes and resource exhaustion, especially useful behind reverse proxies without rate-limiting.
New Prometheus metrics for monitoring:
ipfs_http_gw_concurrent_requests: Current requests being processedipfs_http_gw_responses_total: HTTP responses by status codeipfs_http_gw_retrieval_timeouts_total: Timeouts by status code and truncation status
Tuning tips:
- Monitor metrics to understand gateway behavior and adjust based on observations
- Watch
ipfs_http_gw_concurrent_requestsfor saturation - Track
ipfs_http_gw_retrieval_timeouts_totalvs success rates to identify timeout patterns indicating routing or storage provider issues
Clear provide queue when reprovide strategy changes
Your content sharing strategy changes now take effect cleanly, without interference from previously queued items.
When you change Reprovider.Strategy and restart Kubo, the provide queue is automatically cleared. This ensures only content matching your new strategy will be announced to the network.
A new ipfs provide clear command also allows manual queue clearing for debugging purposes.
Note
Upgrading to Kubo 0.37 will automatically clear any preexisting provide queue. The next time
Reprovider.Intervalhits,Reprovider.Strategywill be executed on a clean slate, ensuring consistent behavior with your current configuration.
🪵 Revamped ipfs log level command
The ipfs log level command has been completely revamped to support both getting and setting log levels with a unified interface.
New: Getting log levels
ipfs log level- Shows default level onlyipfs log level all- Shows log level for every subsystem, including default levelipfs log level foo- Shows log level for a specific subsystem only- Kubo RPC API:
POST /api/v0/log/level?arg=<subsystem>
Enhanced: Setting log levels
ipfs log level foo debug- Sets "foo" subsystem to "debug" levelipfs log level all info- Sets all subsystems to "info" level (convenient, no escaping)ipfs log level '*' info- Equivalent to above but requires shell escapingipfs log level foo default- Sets "foo" subsystem to current default level
The command now provides full visibility into your current logging configuration while maintaining full backward compatibility. Both all and * work for specifying all subsystems, with all being more convenient since it doesn't require shell escaping.
🧷 Named pins in ipfs add command
Added --pin-name flag to ipfs add for assigning names to pins.
$ ipfs add --pin-name=testname cat.jpg
added bafybeigdyrzt5sfp7udm7hu76uh7y26nf3efuylqabf3oclgtqy55fbzdi cat.jpg
$ ipfs pin ls --names
bafybeigdyrzt5sfp7udm7hu76uh7y26nf3efuylqabf3oclgtqy55fbzdi recursive testname
⚙️ Reprovider.Strategy is now consistently respected
Prior to this version, files added, blocks received etc. were "provided" to the network (announced on the DHT) regardless of the "reproviding strategy" setting. For example:
- Strategy set to "pinned" +
ipfs add --pin=false→ file was provided regardless - Strategy set to "roots" +
ipfs pin add→ all blocks (not only the root) were provided
Only the periodic "reproviding" action (runs every 22h by default) respected the strategy.
This was inefficient as content that should not be provided was getting provided once. Now all operations respect Reprovider.Strategy. If set to "roots", no blocks other than pin roots will be provided regardless of what is fetched, added etc.
Note
Behavior change: The
--offlineflag no longer affects providing behavior. Bothipfs addandipfs --offline addnow provide blocks according to the reproviding strategy when run against an online daemon (previously--offline adddid not provide). Sinceipfs addhas been nearly as fast as offline mode since v0.35,--offlineis rarely needed. To run truly offline operations, useipfs --offline daemon.
Removed unnecessary dependencies
Kubo has been cleaned up by removing unnecessary dependencies and packages:
- Removed
thirdparty/assert(replaced bygithub.com/stretchr/testify/require) - Removed
thirdparty/dir(replaced bymisc/fsutil) - Removed
thirdparty/notifier(unused) - Removed
goprocessdependency (replaced with native Gocontextpatterns)
These changes reduce the dependency footprint while improving code maintainability and following Go best practices.
Custom sequence numbers in ipfs name publish
Added --sequence flag to ipfs name publish for setting custom sequence numbers in IPNS records. This enables advanced use cases like manually coordinating updates across multiple nodes. See ipfs name publish --help for details.
Improved ipfs cid
Certain ipfs cid commands can now be run without a daemon or repository, and return correct exit code 1 on error, making it easier to perform CID conversion in scripts and CI/CD pipelines.
While at it, we also fixed unicode support in ipfs cid bases --prefix to correctly show base256emoji 🚀 :-)
Deprecated ipfs stats reprovide
The ipfs stats reprovide command has moved to ipfs provide stat. This was done to organize provider commands in one location.
Note
ipfs stats reprovidestill works, but is marked as deprecated and will be removed in a future release.
🔄 AutoRelay now uses all connected peers for relay discovery
AutoRelay's relay discovery now includes all connected peers as potential relay candidates, not just peers discovered through the DHT. This allows peers connected via HTTP routing and manual ipfs swarm connect commands to serve as relays, improving connectivity for nodes using non-DHT routing configurations.
📊 Anonymous telemetry for better feature prioritization
Per a suggestion from the IPFS Foundation, Kubo now sends optional anonymized telemetry information to Shipyard maintainers.
Privacy first: The telemetry system collects only anonymous data - no personally identifiable information, file paths, or content data. A random UUID is generated on first run for anonymous identification. Users are notified before any data is sent and have time to opt-out.
Why: We want to better understand Kubo usage across the ecosystem so we can better direct funding and work efforts. For example, we have little insights into how many nodes are NAT'ed and rely on AutoNAT for reachability. Some of the information can be inferred by crawling the network or logging /identify details in the bootstrappers, but users have no way of opting out from that, so we believe it is more transparent to concentrate this functionality in one place.
What: Currently, we send the following anonymous metrics:
"uuid": "<unique_uuid>",
"agent_version": "kubo/0.37.0-dev",
"private_network": false,
"bootstrappers_custom": false,
"repo_size_bucket": 1073741824,
"uptime_bucket": 86400000000000,
"reprovider_strategy": "pinned",
"routing_type": "auto",
"routing_accelerated_dht_client": false,
"routing_delegated_count": 0,
"autonat_service_mode": "enabled",
"autonat_reachability": "",
"swarm_enable_hole_punching": true,
"swarm_circuit_addresses": false,
"swarm_ipv4_public_addresses": true,
"swarm_ipv6_public_addresses": true,
"auto_tls_auto_wss": true,
"auto_tls_domain_suffix_custom": false,
"discovery_mdns_enabled": true,
"platform_os": "linux",
"platform_arch": "amd64",
"platform_containerized": false,
"platform_vm": false
The exact data sent for your node can be inspected by setting GOLOG_LOG_LEVEL="telemetry=debug". Users will see an informative message the first time they launch a telemetry-enabled daemon, with time to opt-out before any data is collected. Telemetry data is sent every 24h, with the first collection starting 15 minutes after daemon launch.
User control: You can opt-out at any time:
- Set environment variable
IPFS_TELEMETRY=offbefore starting the daemon - Or run
ipfs config Plugins.Plugins.telemetry.Config.Mode offand restart the daemon
The telemetry plugin code lives in plugin/plugins/telemetry.
Learn more: /kubo/docs/telemetry.md
📦️ Important dependency updates
- update
go-libp2pto v0.43.0 (incl. v0.42.1) - update
p2p-forge/clientto v0.6.1 - update
boxoto v0.33.1 - update
ipfs-webuito v4.8.0 - update to Go 1.25