pub enum NodeCommand {
Show 18 variants
Health(HealthArgs),
Status(StatusArgs),
Lanes(LanesArgs),
Slashes(SlashesArgs),
Pools(PoolsArgs),
Evict(EvictArgs),
Reload(ReloadArgs),
Drain(DrainArgs),
Top(TopArgs),
Register(RegisterArgs),
Bond(BondArgs),
Unbond(UnbondArgs),
Deregister(DeregisterArgs),
RotateKey(RotateKeyArgs),
UpdateMultiaddrs(UpdateMultiaddrsArgs),
UpdateRegion(UpdateRegionArgs),
Lookup(LookupArgs),
Doctor(Box<DoctorArgs>),
}Expand description
Subcommands under decdn node.
Variants§
Health(HealthArgs)
Print a running node’s identity and process uptime.
Status(StatusArgs)
Print a snapshot of the running node’s DHT participation health
via admin_v1_status (issue #741): Kademlia routing-table bucket
fill rates, the network-wide last bucket-refresh time, the
active-staker count, provider-record store utilization, and
republish-scheduler depth. Lets operators diagnose cold-start or
routing-table degradation without scraping Prometheus or reading
logs.
Lanes(LanesArgs)
Print a live snapshot of the running node’s lanes via
admin_v1_lanes (issue #749): per lane the outstanding accrued
claim (micro-USDC), time since the last voucher, and whether the
accrued claim has reached the configured redemption threshold.
Lets operators spot lanes approaching settlement, stale lanes, or
unusually high outstanding balances before they become a
liquidity risk — without scraping metrics or reading logs. Same
admin-URL resolution and timeout semantics as decdn node health.
Slashes(SlashesArgs)
Print every slash the node’s watcher has detected against its own
operator via admin_v1_slashes (#1032, G-NODE-05): per slash the
slashId, offense type, amount, evidence digest, block, and the
30-day appeal-window close time. Lets operators (or keeper scripts)
notice a slash and file decdn appeal slash within the window
without watching the chain directly. Same admin-URL resolution and
timeout semantics as decdn node health.
Pools(PoolsArgs)
Print the running node’s buyer-side PaymentPool state via
admin_v1_pools (#2078): every pool the node’s buy leg tracks, the
deposit it believes each holds, and the per-lane amount it has already
signed away to each provider. This is the node’s spending side — the
mirror of decdn node lanes, which reports what it has earned.
The only way to read this state on a running node: the daemon holds an
exclusive lock on its buyer.redb for its whole lifetime, so no
command can open that file from disk while the node is up. decdn pool list manages a separate, client-owned store and says nothing about
this one. Same admin-URL resolution and timeout semantics as
decdn node health.
Evict(EvictArgs)
Forcibly remove a single blob from the local cache (issue #279). The removal is permanent: the node never serves or re-fetches the hash again. Useful for DMCA takedown and storage reclamation.
Reload(ReloadArgs)
Re-read the running node’s config file and apply hot-reloadable
fields (issue #373). Equivalent to kill -HUP <pid> but goes
through the loopback admin surface, so operator tooling that
already speaks JSON-RPC doesn’t need to also know which PID to
signal. observability.log_level, cache.pinned_hashes,
security.*, the [content] denylist, and [load_shed] are
reloadable; other fields are logged as ignored. The authoritative
list is the module doc of the node’s runtime/reload.rs — when a
section is added there, update this help text too. Both paths
share the same internal mutex, so a concurrent SIGHUP and
decdn node reload queue rather than race. Requires the node to
have been started with decdn-node run --config <path> — without
a path on disk there’s nothing to re-read.
Drain(DrainArgs)
Trigger graceful shutdown of the running node via admin_v1_drain
(issue #244, adr/appendix-local-admin-http.md). Equivalent to kill -TERM <pid> but goes
through the loopback admin surface, so operator tooling that already
speaks JSON-RPC doesn’t need to also know which PID to signal. The
runtime begins the same graceful shutdown sequence SIGTERM triggers
(stops accept loops, waits for in-flight transfers, flushes cache).
Fire-and-forget semantics: this command returns drain_initiated=true
as soon as the trigger is queued. The response does not mean shutdown
is complete — it means the runtime has been asked to shut down, and
the connection may close before the node fully exits because the
admin server is one of the first surfaces to stop. Observe completion
via process exit (systemd/K8s will notice) or by polling decdn node health until the connection is refused.
Top(TopArgs)
Render a live (every --interval-ms) view of node activity by
scraping the running node’s /metrics HTTP endpoint (issue
#275). Shows active streams, cache hit rate, and cache bytes
returned — the operator-visible signal the issue calls “bytes
served” maps to decdn_cache_bytes_returned_total until the
network-side cdn/client/v1 egress counter (#317) lands.
Register(RegisterArgs)
Register this node on-chain via CapacityBond.registerNode (ADR 019
§ Step 2.3). Loads the local iroh node key and Ethereum keystore,
builds the EIP-712 bindingSignature and the ed25519 ownership
signature locally, and submits the registration transaction. This
is the only node subcommand that talks to the chain rather than a
running node’s admin RPC.
Phase 2.1/2.2 (approve + bond + declareMbps) are a
precondition: the contract reverts if the operator’s bond does not
cover minBond / the declared-capacity curve. Pass --dry-run to
print the parameters and signatures without submitting.
Bond(BondArgs)
Stake to a capacity tier on-chain via CapacityBond.bond +
declareMbps (ADR 019 § Step 2.1–2.2). Idempotent: tops the active
bond up to max(minBond, bondRequired(mbps)), approving and bonding
only the shortfall, so re-running after a partial failure converges
rather than over-bonding. Run this before decdn node register. Pass
--dry-run to print the plan without submitting.
Unbond(UnbondArgs)
Lower the on-chain bond via CapacityBond.requestUnbond + unbond
(ADR 026 § Capacity-bond curve) — the reverse of decdn node bond.
State-aware: with no request in flight it declares the tier down (if
needed) and starts the unbonding window; while one is maturing it
reports the unlock time and exits non-zero; once matured it withdraws.
Note that a request in flight makes the node INACTIVE for the whole
window. Pass --dry-run to print the plan without submitting.
Deregister(DeregisterArgs)
Leave the active node set on-chain via CapacityBond.deregisterNode
(ADR 003 § Node Registry) — the reverse of decdn node register, and
the first leg of a full bond exit. Clears the declared capacity tier,
which is what releases the bondRequired(declaredMbps) floor that
decdn node unbond enforces.
This does NOT return the bond: it stays deposited and fully slashable.
Follow with decdn node unbond --all to start the unbonding window,
then re-run it after the window to withdraw. Pass --dry-run to print
the plan without submitting.
RotateKey(RotateKeyArgs)
Rotate an operator key and keep the on-chain binding in step
(adr/appendix-operator-key-rotation.md, #1034). --key chooses which
key, because the two paths are not comparable in cost or effect.
--key iroh rebinds the wire node id through
CapacityBond.bindNodeId. One transaction, no downtime beyond a
restart, and the Ethereum address — with the bond, the declared tier,
firstBondedAt, and every lane funded against this operator — is untouched. The old
and new node ids swap slashability in the same block, so there is no
window in which the operator cannot be slashed.
--key eth moves the whole on-chain identity, because no rebinding API
exists for the address: deregister, wait out the full unbonding window,
withdraw, then re-bond and re-register from a new address.
firstBondedAt — and with it the governance age-ramp — resets. Like
decdn node unbond, the phase is read from chain state rather than
passed as a flag, so one command drives the whole window.
Neither path restarts the daemon: the iroh key is not hot-reloadable,
so drain (decdn node drain), stop, rotate, restart stays the
operator’s sequence. Pass --dry-run to print the plan — and, on the
iroh path, both signatures — without submitting or touching any key
file.
UpdateMultiaddrs(UpdateMultiaddrsArgs)
(Re)publish this node’s dialable QUIC addresses on-chain via
CapacityBond.updateMultiaddrs (#1908). The one-command fix for a node
that registered an empty multiaddr set (decdn node register with no
--multiaddr) and is therefore stranded on the iroh relay path: it
promotes direct addresses without a destructive deregister/re-register
cycle (which register alone cannot do — a second register reverts
NodeAlreadyRegistered).
Like the other on-chain node subcommands this talks to the chain, not
a running node’s admin RPC, and signs with the operator Ethereum key.
The node must be active; the contract’s guardrails — the
maxMultiaddrSize byte ceiling and the multiaddrUpdateCooldown
between updates — are pre-checked and reported before the send. Pass
--dry-run to print the plan (packed size, ceiling, cooldown state)
without submitting.
UpdateRegion(UpdateRegionArgs)
(Re)attest this node’s region on-chain via CapacityBond.updateRegion
(ADR 030). The one-command fix for a node that registered the wrong
regionHint (decdn node register --region) or whose operator has
physically relocated: it corrects the region without a destructive
deregister/re-register cycle (which register alone cannot do — a second
register reverts NodeAlreadyRegistered).
Like the other on-chain node subcommands this talks to the chain, not
a running node’s admin RPC, and signs with the operator Ethereum key. The
region is validated as an ISO 3166-1 alpha-2 code CLI-side — the contract
only length-checks and would otherwise store a garbage string. The node
must be active; the contract’s regionStabilityWindow cooldown between
updates is pre-checked and reported before the send. Pass --dry-run to
print the plan (current region, new region, cooldown state) without
submitting.
Lookup(LookupArgs)
Unpaid client-side discovery of active nodes via
CapacityBond.getRegisteredNodes (#1481). Maps node-ids/regions to
operator Ethereum addresses — the input decdn fetch --provider-address needs — without spending anything: it builds a
signer-less read-only provider and never loads a keystore, unlike
every other on-chain node subcommand above.
With neither --node-id nor --region, lists every active node.
Pass --probe to additionally rank the (region-shortlisted)
candidates by measured cdn/probe/v1 round-trip time; without it,
candidates are listed with no RTT.
Doctor(Box<DoctorArgs>)
Diagnose config, on-disk state, disk budget, and reachability.
Trait Implementations§
Source§impl Debug for NodeCommand
impl Debug for NodeCommand
Source§impl FromArgMatches for NodeCommand
impl FromArgMatches for NodeCommand
Source§fn from_arg_matches(__clap_arg_matches: &ArgMatches) -> Result<Self, Error>
fn from_arg_matches(__clap_arg_matches: &ArgMatches) -> Result<Self, Error>
Source§fn from_arg_matches_mut(
__clap_arg_matches: &mut ArgMatches,
) -> Result<Self, Error>
fn from_arg_matches_mut( __clap_arg_matches: &mut ArgMatches, ) -> Result<Self, Error>
Source§fn update_from_arg_matches(
&mut self,
__clap_arg_matches: &ArgMatches,
) -> Result<(), Error>
fn update_from_arg_matches( &mut self, __clap_arg_matches: &ArgMatches, ) -> Result<(), Error>
ArgMatches to self.Source§fn update_from_arg_matches_mut<'b>(
&mut self,
__clap_arg_matches: &mut ArgMatches,
) -> Result<(), Error>
fn update_from_arg_matches_mut<'b>( &mut self, __clap_arg_matches: &mut ArgMatches, ) -> Result<(), Error>
ArgMatches to self.Source§impl Subcommand for NodeCommand
impl Subcommand for NodeCommand
Source§fn augment_subcommands<'b>(__clap_app: Command) -> Command
fn augment_subcommands<'b>(__clap_app: Command) -> Command
Source§fn augment_subcommands_for_update<'b>(__clap_app: Command) -> Command
fn augment_subcommands_for_update<'b>(__clap_app: Command) -> Command
Command so it can instantiate self via
FromArgMatches::update_from_arg_matches_mut Read moreSource§fn has_subcommand(__clap_name: &str) -> bool
fn has_subcommand(__clap_name: &str) -> bool
Self can parse a specific subcommandAuto Trait Implementations§
impl Freeze for NodeCommand
impl RefUnwindSafe for NodeCommand
impl Send for NodeCommand
impl Sync for NodeCommand
impl Unpin for NodeCommand
impl UnsafeUnpin for NodeCommand
impl UnwindSafe for NodeCommand
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
Source§fn in_current_span(self) -> Instrumented<Self> ⓘ
fn in_current_span(self) -> Instrumented<Self> ⓘ
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read more