Early-stage software. Shurli is experimental and built with AI assistance. It will have bugs. Not recommended for production or safety-critical use. Read the disclaimer.
Network Tools

Network Tools

Shurli provides P2P network diagnostic commands that mirror familiar system utilities. These work both standalone (create a temporary P2P host) and through the daemon API (use the existing host for faster operation).

Table of Contents


ping

P2P ping - measures round-trip time and connection path to a peer.

Usage

# Standalone (creates temp host, pings, exits)
shurli ping <peer> [-c N] [--interval 1s] [--json] [--config path]

# Via daemon (reuses existing host - faster)
shurli daemon ping <peer> [-c N] [--interval 1s] [--json]

Behavior

ModeBehavior
-c N (N > 0)Send N pings, print per-ping line, summary at end
No -c flagContinuous pinging until Ctrl+C, summary on exit
--interval 1sTime between pings (default 1s)
--jsonJSON output (one line per ping result + final stats)

Output

Plain text (default):

PING home-server (12D3KooWPrmh...):
seq=1 rtt=45.2ms path=[RELAYED]
seq=2 rtt=42.1ms path=[DIRECT]
seq=3 rtt=43.0ms path=[DIRECT]
^C
--- home-server ping statistics ---
3 sent, 3 received, 0% loss, rtt min/avg/max = 42.1/43.4/45.2 ms

JSON (--json):

{"seq":1,"peer_id":"12D3KooWPrmh...","rtt_ms":45.2,"path":"RELAYED"}
{"seq":2,"peer_id":"12D3KooWPrmh...","rtt_ms":42.1,"path":"DIRECT"}
{"seq":3,"peer_id":"12D3KooWPrmh...","rtt_ms":43.0,"path":"DIRECT"}
{"sent":3,"received":3,"lost":0,"loss_pct":0.0,"min_ms":42.1,"avg_ms":43.4,"max_ms":45.2}

Connection Path

Each ping shows whether the connection went through the relay or directly:

PathMeaning
[DIRECT]Peer-to-peer (hole-punched or same LAN)
[RELAYED]Via circuit relay server

Direct connections have lower latency. If pings start as RELAYED and switch to DIRECT, DCUtR hole-punching succeeded.

Ping Allow/Deny

Peers can disable ping responses in their config:

protocols:
  ping:
    enabled: false   # silently drop ping requests

When disabled, the peer doesn’t register the ping-pong stream handler. Pings will time out - same behavior as a firewall dropping ICMP.

How It Works

  1. Open a libp2p stream to the target peer using the ping-pong protocol (/shurli/ping/1.0.0)
  2. Send "ping\n" on the stream
  3. Wait for "pong\n" response
  4. Measure round-trip time
  5. Check connection type (direct vs relayed) from stream metadata

traceroute

P2P traceroute - shows the network path to a peer with per-hop latency.

Usage

# Standalone
shurli traceroute <peer> [--json] [--config path]

# Via daemon API
curl -X POST -H "Authorization: Bearer $(cat ~/.config/shurli/.daemon-cookie)" \
     -d '{"peer":"home-server"}' \
     --unix-socket ~/.config/shurli/shurli.sock \
     http://localhost/v1/traceroute

Path Visualization

Traceroute paths: relayed (2 hops via relay with latency) vs direct (1 hop, lower latency)

Output

Relayed connection:

traceroute to home-server (12D3KooWPrmh...), max 3 hops:
 1  12D3KooWK... (relay)  203.0.113.50:7777  23.0ms
 2  12D3KooWPrmh... (home-server)  via relay  45.0ms
--- path: [RELAYED via relay-server/0.1.0] ---

Direct connection:

traceroute to home-server (12D3KooWPrmh...), max 3 hops:
 1  12D3KooWPrmh... (home-server)  10.0.1.50:9000  2.0ms
--- path: [DIRECT] ---

What It Shows

  • Whether the connection is direct or through a relay
  • Latency to each hop (relay, then peer)
  • Relay server’s software version (from peerstore AgentVersion)
  • Peer addresses

Implementation

This is not true multi-hop tracing (libp2p doesn’t support TTL). Instead, it inspects connection metadata:

  1. Check if the connection to the peer goes through a relay (multiaddr contains /p2p-circuit)
  2. If relayed: measure RTT to relay separately, then RTT to peer through relay
  3. If direct: single hop with measured RTT
  4. Report the agent version of intermediate nodes from the peerstore

This gives the real diagnostic information needed: where is my traffic going, and how fast is each segment.


resolve

P2P nslookup - resolves peer names to peer IDs.

Usage

# Standalone (no network needed)
shurli resolve <name> [--json] [--config path]

# Via daemon API
curl -X POST -H "Authorization: Bearer $(cat ~/.config/shurli/.daemon-cookie)" \
     -d '{"name":"home-server"}' \
     --unix-socket ~/.config/shurli/shurli.sock \
     http://localhost/v1/resolve

Output

Plain text:

home-server → 12D3KooWPrmh163sTHW3mYQm7YsLsSR2wr71fPp4g6yjuGv3sGQt (source: local_config)

JSON (--json):

{
  "name": "home-server",
  "peer_id": "12D3KooWPrmh163sTHW3mYQm7YsLsSR2wr71fPp4g6yjuGv3sGQt",
  "source": "local_config"
}

Resolution Sources

SourceMeaning
local_configResolved from names: section in config.yaml
peer_idInput was already a valid peer ID (direct parse)

No Network Required

resolve reads from local config only - it doesn’t contact the network or start a P2P host. Resolution is instant.

Names are configured in config.yaml:

names:
  home-server: "12D3KooWPrmh163sTHW3mYQm7YsLsSR2wr71fPp4g6yjuGv3sGQt"
  laptop: "12D3KooWNq8c1fNjXwhRoWxSXT419bumWQFoTbowCwHEa96RJRg6"

Standalone vs Daemon

All network tools work in two modes:

ModeCommandSpeedWhen to Use
Standaloneshurli ping home-serverSlower (creates temp host, bootstraps DHT)One-off diagnostics, daemon not running
Daemonshurli daemon ping home-serverFaster (reuses existing host + connections)Repeated diagnostics, scripting

Standalone Startup

When running standalone, the tool:

  1. Loads config to find relay addresses, bootstrap peers, and names
  2. Creates a temporary libp2p host
  3. Bootstraps into the DHT (client mode)
  4. Connects to relay servers
  5. Finds the target peer via DHT or relay fallback
  6. Runs the diagnostic
  7. Shuts down the host

This takes 5-15 seconds for initial setup. The daemon mode skips all of this.

Shared Logic

Both modes use the same underlying functions:

  • p2pnet.PingPeer() - streaming ping with configurable count and interval
  • p2pnet.ComputePingStats() - min/avg/max/loss statistics
  • p2pnet.TracePeer() - connection path analysis

System Utility Comparison

System ToolShurli EquivalentWhat It Does
pingshurli pingMeasure RTT to a peer
tracerouteshurli tracerouteShow path to a peer (direct vs relay)
nslookup / digshurli resolveResolve name to peer ID
ss / netstatshurli daemon peersShow connected peers
systemctl statusshurli daemon statusShow daemon status

Last Updated: 2026-02-22