Beersy
BRC-177

Wallet-Enforced Expiry for `noSend` Actions

If you hand someone a signed Bitcoin payment but they never actually broadcast it, your wallet still treats the money as locked up, sometimes far more than you meant to spend, with no way to get it back short of waiting forever. App-level timers do not help because they cannot undo a signature that has already left the wallet. This gives a way to bound that exposure and automatically free the funds after a deadline, or explicitly commit them forever.

Ty Everettchanged 16 Oct 202623 min read

Reference for an AI

Everything an assistant needs to answer questions about BRC-177 accurately, including what it depends on.

Summary

Why
Handing an unbroadcast transaction to someone else can lock up wallet funds indefinitely because no existing mechanism lets the wallet reclaim or bound that reservation.
What
BRC-177 defines a wallet-enforced expiry mechanism for BRC-100 , letting a wallet reclaim unpublished funds after a deadline or permanently commit them as spent.
How
The wallet funds the through a small dedicated output, the action with an expiry (seconds, timestamp, block height, or never), and either reclaims that anchor if the deadline passes unused or waits for an explicit authorized sendWith request to publish it.

What this lets you do

  • Create a noSend action with a time, timestamp, block-height, or never expiry label
  • Bound the wallet value a handed-off unpublished transaction can lock up
  • Reclaim a finite protected action's funds automatically after its deadline
  • Abort and revoke a released finite action before it is accepted on-chain
  • Issue a portable statement so other wallets can verify a protected action's deadline

Written by claude-sonnet-5 from the specification text. Where the two differ, the original is correct.

noSend actionexpiry deadlinreclaim or bro

The specification

Abstract

This specification defines the BRC-111 module p nosend expiry for bounded, prefunded BRC-100 noSend actions and dependent action batches. Finite modes reclaim an unpublished root after a deadline. The explicit never mode permanently treats released payment value as sent and never reclaims it. The wallet publishes only on an explicit, authorized sendWith request; otherwise a recipient or application may publish them.

Expiry may be expressed as seconds, a Unix timestamp, a block height, or never. Two-phase signing and token-aware chained actions use the existing BRC-100 methods. Atomic wallet persistence does not imply atomic network or settlement.

Motivation

A noSend transaction may be handed to an application, recipient, or other broadcaster and remain unbroadcast indefinitely. During that time its inputs are reserved. If ordinary wallet coin selection gave the transaction a large input and expected significant change, most of that input's value can remain unavailable even though only a small payment was intended.

Applications can implement timers, but an application timer does not release the wallet's reservation and cannot invalidate a signed transaction already given to another party. Bitcoin timelocks provide a lower bound on when a transaction may be mined; they do not make a transaction invalid after a deadline.

This specification uses the model directly. A small, purpose-built funding output bounds the value reserved by the protected action. Spending that output in a makes the protected action a double spend. No new wallet method, transaction field, or script template is required.

Normative Language

The key words MUST, MUST NOT, SHOULD, SHOULD NOT, and MAY in this document are to be interpreted as described in RFC 2119 and RFC 8174 when they appear in all capitals.

Specification

Label namespace

This specification defines BRC-111 nosend and the following exact action-label forms:

LabelMeaning
p nosend expiry seconds <duration>Expire <duration> seconds after activation
p nosend expiry timestamp <unixSeconds>Expire at the stated Unix time
p nosend expiry blockheight <height>Expire when the wallet observes a best-chain height greater than or equal to <height>
p nosend expiry neverNo deadline or reclamation after release

An optional exact label p nosend batch enables the protected batch rules below. It carries no parameter and may appear at most once. Without it, the single-action no-change isolation rule remains. never takes no numeric value. Unknown forms and duplicate lifecycle or batch labels fail before funding.

Examples:

p nosend expiry seconds 300
p nosend expiry timestamp 1798761600
p nosend expiry blockheight 1000000

The fixed words are lowercase ASCII and separated by one space. Each value MUST be a canonical unsigned base-10 integer: digits only, no sign, and no leading zero unless the value is zero. duration MUST be greater than zero. unixSeconds is the number of elapsed seconds since 1970-01-01T00:00:00Z, ignoring leap seconds.

A protected root MUST contain exactly one p nosend expiry ... label. A batch child MAY omit it and inherit its roots' policies as specified below. A wallet MUST reject malformed forms, unknown expiry modes, duplicate expiry labels, or values outside its safely supported integer and scheduling range. Other ordinary and supported module labels MAY appear on the action.

Per BRC-111, a wallet that does not support module ID nosend MUST reject the request rather than treating the label as ordinary metadata.

In a distributed wallet, the component that owns durable action state and deadline monitoring MUST advertise or otherwise establish BRC-177 support before prefunding begins. A client MUST NOT create the funding transaction when its authoritative storage or monitor cannot persist and enforce the protected lifecycle.

Protected action

An action with a valid expiry label, or a batch child inheriting registered root policies, is a protected action. A root directly spends dedicated wallet-controlled funding, its revocation anchor; children depend on that through their ancestors. A member is released once a wallet signature capable of authorizing its spend has left the wallet. A root releases its anchor signature. A transaction that spends a finite root's anchor back to the wallet is its reclaim transaction; never roots have no reclaim transaction.

Construction MUST set options.noSend:true and MUST NOT use returnTXIDOnly. noSendChange is allowed under the protected batch rules. Construction and publication are separate calls: construction MUST NOT include sendWith. A subsequent batch-only createAction with sendWith may explicitly authorize publication as specified below. An implicit batch commit, an unrelated action, or signAction is not publication authorization.

All ordinary BRC-100 validation, spending authorization, and permission checks still apply. This module adds expiry behavior; it does not grant permission to spend.

Prefunding

Before it returns any signed or signable representation of a protected root, the wallet MUST:

  1. Determine the value required by the requested outputs, supplied explicit inputs, and a fee-safe serialization of the protected action.
  2. Create a normal funding transaction with one dedicated output controlled by the wallet and tracked in its internal default . The output MUST fund the protected action under the wallet's current fee and output policies. Finite roots also require an economical reclaim output after its fee; never roots require no reclaim-fee allowance.
  3. Broadcast the funding transaction immediately and obtain acceptance from at least one transaction processor under the wallet's ordinary immediate-broadcast policy.
  4. Construct the protected action with the revocation anchor as its only automatically selected wallet input.

Except for the bounded batch budget below, the protected action MUST contain no automatically generated wallet change. A wallet SHOULD size the anchor to avoid material overpayment and MUST fail if safe isolation is impossible. A root may reuse an already accepted, dedicated funding output with sufficient verified Bitcoin , exclusive ownership and applicable authorization instead of creating new funding. This permits preparation before disconnection; it does not permit an unavailable remote store or unknown funding state to be treated as valid.

The funding transaction itself MAY have ordinary change because it is broadcast before the protected action is released. That change is not reserved by the protected action.

The anchor MUST be reserved exclusively for the protected action until either the protected action is observed on the network or the anchor is reclaimed. The returned for the protected action MUST contain the funding transaction and the supporting data required by BRC-62 and BRC-100.

When the protected action is finalized, the wallet's signature for the anchor input MUST commit to the complete input and output set, normally with SIGHASH_ALL. Caller-supplied inputs MAY still require external .

If funding acceptance cannot be established, the wallet MUST fail before release. An invalid or conflicting funding transaction invalidates its descendants; the wallet MUST reconcile them rather than present them as available for settlement.

Protected action batches

These rules specify the public behavior analogous to 's action batch planner; storage RPCs, lease lengths, allocation algorithms and are implementation details, not BRC-100 additions.

  1. A root has one expiry label and p nosend batch. The wallet isolates a dedicated budget, including any authorized batch fee headroom, and discloses its maximum encumbered value before approval. Only that budget and explicitly designated token/resource inputs may be encumbered. Surplus in unrelated satoshi or fungible-token holdings MUST first be released through an authorized, processed preparation/split, or construction fails. Resources and indivisible rights MUST NOT be split as fungible funding.
  2. A child joins by an explicit input or noSendChange referencing a fully signed staged parent, and carries p nosend batch. It MAY omit the expiry label and inherit the roots' persisted policies; a supplied label MUST match every inherited policy exactly. Time adjacency, originator equality or an unrelated noSend call does not join a graph. Unrelated remains separate.
  3. Parents' signed bytes and TXIDs MUST be fixed before children are signed. Validate a topologically ordered DAG, exact sources, scripts, , fees, output positions and all applicable token/profile rules. Reject cycles, conflicting representations and duplicate spends within the graph. A changed ancestor invalidates dependent signatures/IDs; reconstruct and reauthorize affected descendants rather than patch their references silently.
  4. Bounded wallet-owned satoshi remainder may travel through noSendChange within the graph. It remains designated batch funding, outside ordinary available balances. Token dependencies use explicit outpoints and the token module's plan/evidence rules; noSendChange does not make tokens generic fee funding. Extra funding requires an accepted dedicated root, consent and graph-wide reservation updates. Joining graphs preserves every root and policy; a never promise MUST NOT be made for a descendant of a reclaimable root.
  5. Every protected member MUST depend on at least one registered root anchor. Record which members depend on each anchor. Finite roots retain their own immutable deadlines; a descendant expires if any still-unaccepted finite ancestor root reaches its deadline. Evaluate each time or height predicate in its own units; do not numerically compare heights with timestamps. Same-policy graphs may join; mixed policies are allowed only when the caller omits an overriding expiry label and authorizes all effective restrictions.
  6. Before returning any signed member, atomically persist its exact bytes, dependency graph, funding/token reservations, consent, root policies and released-signature exposure in authoritative durable storage. In-memory staging MAY optimize planning but MUST NOT be its only record after release. Lease expiry, destruction or restart MUST NOT free an input with a usable released signature. Persisted exact bytes and records must support recovery without requiring the original client session or creating a second payment.
  7. sendWith requests publication of named retained actions and their unpublished ancestor closure. Before any submission the wallet MUST authenticate that closure, establish publication authority, obtain all applicable consent, check deadlines and reconcile known conflicts. Missing parents, conflicting roots, unsupported profiles or missing authorization fail the request before publishing a ready subset. Imported foreign ancestors may be carried as authenticated transaction evidence; naming an unknown TXID is not an import or authority to publish it. Every independent requested transaction needs its own ordinary authorization; membership cannot silently capture other work.
  8. Persist the exact submission intent before external effects. Publish complete consensus-final members in dependency order or through a processor accepting their dependency package. Return normal per-TXID sendWithResults for the explicitly requested IDs; retain ancestor outcomes in durable action state. Immediate mode reports the attempted result. Delayed mode durably queues the intent but MUST recheck finite root deadlines before first submission; merely queued work does not cancel reclamation. Non-final members additionally obey BRC-207's processor-coordination contract; this is not permission to bypass it.
  9. An atomic storage commit is not all-or-nothing Bitcoin/overlay publication. Track each member's attempted, accepted, admitted, confirmed, failed or uncertain facts separately. An accepted root cancels its reclaim schedule; its descendants may still fail. Resume authorized recovery of that accepted root's descendants after its former deadline: the deadline limits first root publication, not completion of every descendant. Independent finite roots still retain their own deadlines. Never claim rollback of a published prefix.
  10. Retries use the same signed bytes and reconcile processor/overlay evidence before resubmission. A lost response is uncertain, not proof of rejection. A winning anchor reclaim invalidates only descendants of that anchor whose root did not win. Release other reservations only after their separate exposure is reconciled. An already spent anchor cannot revoke descendants; independently expiring a later offer requires its own dedicated anchor. A signature usable without that anchor remains separate exposure; do not claim it expired or free its input merely because the anchored graph lost.

Cross-wallet delivery carries complete Bitcoin and applicable token dependency evidence and authenticated lifecycle metadata. The receiver independently validates, authorizes, persists and extends its own graph; it does not share the sender's workspace or inherit the sender's permissions. BRC-207's declared attested-admission profile permits token descendants before overlay settlement. Without an applicable profile, ordinary token admission still applies.

Activation and deadline

The root's expiry becomes active when the wallet durably commits it, immediately before returning the first signed or signable representation to the caller. The wallet MUST persist the label, action reference, anchor outpoint, computed deadline (or never), whether an anchor signature has been released, and lifecycle state before returning. It MAY also persist the activation time; the computed deadline remains authoritative. Children persist their root references and inherited absolute deadlines; they neither activate a new duration nor require an already accepted root's former deadline to remain in the future.

For seconds, the wallet MUST add duration to the activation time and persist the resulting absolute Unix-second deadline. Restarting the wallet MUST NOT restart the duration.

For timestamp, the supplied time MUST be strictly later than the wallet's current time at activation. For blockheight, the supplied height MUST be greater than the wallet's current best-chain height at activation. If an absolute deadline is no longer in the future after prefunding, the wallet MUST fail without releasing the protected action; the anchor remains ordinary wallet-controlled value.

Finite deadlines are immutable after activation. Extending a deadline or switching between finite and never requires a new action and safe resolution of the old exposure. Inherited child references never restart a relative duration.

Never-expiry and sent accounting

p nosend expiry never has no deadline, hidden timeout or reclaim transaction. It is optional support: unsupported wallets MUST reject it before funding and MUST NOT substitute a finite deadline. The authoritative wallet/storage must support this lifecycle, including backup and multi-device synchronization.

Upon release the wallet MUST permanently debit the authorized payment and designated funding as sent/committed, exclude its inputs from ordinary selection, and MUST NOT schedule, retain for execution or submit an anchor reclaim. It MUST NOT reclaim because of inactivity, delivery failure, lease expiry, restart, loss of an application, abortAction or a later change in wallet policy. Dependent designated change remains batch-only until actually accepted under the applicable Bitcoin/token rules. It is neither a second debit nor available ordinary change. A verified winning spend may settle or reconcile the recorded facts; reconciliation is not permission to manufacture a reclaim.

This is the wallet's irrevocable disposition policy, not proof of broadcast, mining, overlay admission or protection against another party's conflicting spend. Normal BRC-100 statuses retain their meanings; use durable sent/committed accounting without inventing a broadcast result. Explicit authorized publication and status/proof tracking remain available. If no signature capable of consuming the funding was released, cancellation may safely release that funding.

Wallets SHOULD use a clock that is resistant to simple application manipulation. A block-height deadline MUST use the wallet's canonical best-chain tracker. Once a height deadline has triggered, a later reorganization MUST NOT reactivate the protected action.

signAction

A protected createAction MAY return signableTransaction when caller-supplied inputs require unlocking scripts. The root's expiry is already active; it does not wait for signAction. A signable root MUST withhold its anchor signature until signAction. A signable child MUST withhold at least one wallet-controlled input signature needed to complete that child; its ancestors' previously released signatures remain exposed. If no such withholding is possible, record the member as released before returning it and apply the same lifecycle protections.

For a protected action, signAction MUST:

  • inherit the original expiry label and anchor reservation through the BRC-100 action reference;
  • retain options.noSend: true;
  • reject sendWith on this signing call, and reject completion at/after a still-applicable finite deadline;
  • reject completion after reclamation has begun; and
  • preserve the committed input and output set.

Before returning a completed transaction, the wallet MUST durably record release. Finite modes use the reclaim rules below; never forbids reclaim. Batch descendants inherit their roots' persisted lifecycle and cannot silently reset it.

The wallet MUST apply the same monitoring and reclamation behavior whether the protected action is completed directly by createAction or later by signAction, regardless of which caller supplies the non-anchor unlocking scripts.

Before expiry

Without an explicit authorized sendWith publication request, the wallet MUST NOT broadcast or enqueue the protected action. Merely creating, signing or committing a batch does not request publication. Explicit publication follows the same deadline, and conflict rules as external publication.

The wallet MUST monitor the protected transaction when its txid is known and MUST monitor the revocation anchor in all cases. For each root independently, if the wallet establishes that root's mining or processing acceptance before expiry, it MUST cancel that root's reclamation and move it into ordinary BRC-100 broadcast/proof tracking. A child-only response, an orphan acknowledgement or overlay admission alone does not establish an unresolved root's processing acceptance. Expiry is a deadline for broadcast, not a deadline for confirmation.

If the anchor is observed spent but the wallet cannot obtain or validate the spending transaction, it MUST stop treating the anchor as reclaimable and investigate through its normal transaction-status process. It MUST NOT report successful reclamation merely because the protected txid is unknown.

Expiry and reclamation

For a finite root only, when its deadline is reached without observed processing acceptance, the wallet MUST reconcile any in-flight submission before choosing the following actions. It MUST NOT knowingly submit an original and a reclaim concurrently; uncertain external races remain possible. The wallet MUST:

  1. Reject further signAction and wallet-broadcast requests for the protected action.
  2. Check the protected action and anchor through its configured transaction-status services.
  3. If no valid anchor signature has ever been released, abort the unsigned action and return the still-unspent anchor to ordinary default-basket coin selection. No reclaim transaction is needed because the caller cannot produce a valid spend of the anchor.
  4. Otherwise, if the anchor still appears unspent, construct or retrieve a previously signed reclaim transaction that spends it to a fresh wallet-controlled output in the internal default basket.
  5. Broadcast the reclaim transaction immediately, without delayed-broadcast behavior.
  6. Persist and retry reclamation after transient failures until the reclaim transaction is proven, the protected action is observed, or another transaction is proven to have spent the anchor.

The reclaim transaction SHOULD use the anchor as its only input. Its output equals the anchor value less its network fee. Funding and reclamation fees are borne by the wallet owner.

A wallet MAY construct, sign, validate, and durably store the reclaim transaction before it releases a finite root. This permits an authoritative storage monitor without wallet keys to enforce the deadline after a restart or while wallet clients are offline. When a deployment relies on such a keyless monitor, it SHOULD pre-sign the reclaim before release. A pre-signed reclaim MUST remain internal to the wallet or its trusted storage services until reclamation is authorized, and the wallet MUST verify that it spends only the anchor to wallet-controlled value under its recorded fee policy.

Once the reclaim transaction is mined, the protected action conflicts with an already-spent outpoint and is invalid on that chain. Before then, expiry and reclaim broadcast do not create consensus finality: a protected action broadcast at nearly the same time may race the reclaim transaction. Wallets MUST report the transaction that actually wins and MUST NOT describe a pending or merely submitted reclaim as final.

If the protected action is first observed after a reclaim submission may already have occurred, the wallet MUST stop initiating or retrying reclaim submissions but MUST retain proof tracking for both transactions. Neither an observation nor a processor response resolves the race; only the wallet's normally validated proof evidence may expose the winning transaction's outputs as spendable.

Normal proof depth and reorganization handling apply to the reclaim transaction. Applications and recipients SHOULD broadcast with enough margin for the wallet to observe acceptance before the deadline.

Abort and early revocation

For a released finite root, abortAction starts the reclaim process if the root has not been accepted. A child abort MUST NOT silently reclaim a shared ancestor and cancel sibling payments: obtain consent for the complete affected set first, or reject the requested cancellation. Accepted ancestors cannot be reclaimed. For a released never action, abort MUST return an explicit error; it cannot revoke the disposition or release its inputs. Unreleased children may be discarded without freeing any still-exposed ancestors. Local cleanup never revokes bytes.

If a member has not been released, abortAction MUST permanently prevent signAction for that reference. Its reservation may be released only after reconciling all dependent exposure. Returning an anchor to ordinary selection without reclamation is allowed only for an unreleased root whose anchor cannot be spent by any released member; aborting a child never frees an exposed ancestor.

Before activation, an implementation MAY discard an unreleased candidate and return an accepted funding output to ordinary default-basket coin selection without creating a reclaim transaction, because no protected transaction has been exposed.

Persistence and coordination

Lifecycle state MUST survive restarts, backup and synchronization. Multiple devices/storage writers MUST coordinate anchors, graph reservations and submission intents. Every writer enforces the same finite deadline or permanent never disposition and the prohibition on unsolicited publication.

Only the authoritative active storage or monitor SHOULD initiate reclamation. Synchronized lifecycle merges MUST NOT regress an action from a state in which expiry or reclamation has already begun merely because another device reports a later wall-clock update. A reclaim output MUST remain unavailable for wallet coin selection until the wallet has validated proof that the reclaim won; synchronization alone is not proof.

This specification introduces no new BRC-100 method or response field and no new public action status. Implementations MAY keep detailed states such as active, broadcast-observed, reclaiming, reclaimed, and conflicted internally. Existing listActions behavior and BRC-111 permission checks apply to queries using the module label.

Application Communication

Action labels are wallet metadata; they are not committed into the Bitcoin transaction and are not automatically delivered in BEEF. An application that gives the transaction to a recipient MUST communicate the deadline separately using its own protocol. If the recipient must authenticate that deadline, the application SHOULD bind it to the transaction or anchor outpoint with an authenticated message or signature.

Delivery MUST identify each unresolved root's network, anchor and root TXID, plus either never or its effective absolute timestamp/block-height deadline. Relative seconds MUST be converted from the authoritative activation record, not restarted on receipt. The application binds these facts and the dependent transaction bytes through its authenticated delivery protocol. Missing lifecycle facts prevent a claim that a received chain is non-reclaimable. never is a sender-wallet promise, not a Bitcoin script condition.

Portable lifecycle statements

For cross-wallet protected graphs, a wallet MAY issue a portable statement of its own authoritative root policy. Issuance requires the complete root with all unlocking scripts fixed and its final TXID; a provisional/signable root cannot yet receive a statement. The exact statement object has these fields, serialized in this order as compact UTF-8 JSON without whitespace or escapes:

{"version":1,"network":"mainnet","rootTXID":"6de6d9100fce8da9a58057c1aa06d1e1e2e9ab2d4f73219e2b75d4d9e24acd41","anchor":"3a70c52b24687a6d197ef362ad11f68c0e5b8419457df6fc1dc06a5851baefb4.0","mode":"never","value":null}

This is a shape example, not transaction evidence. network is mainnet or testnet; TXIDs are lowercase display-order hex and the anchor is canonical BRC-36 dot notation. mode is timestamp, blockheight or never. value is a nonnegative safe integer absolute deadline for the first two and exactly null for never. Relative seconds are converted from the persisted activation record. The root's actual bytes MUST directly spend the anchor. Duplicate or unknown fields, mismatched source facts and noncanonical values fail.

The message is UTF-8 BRC177-LIFECYCLE-V1\n (one LF) followed by that canonical JSON. createSignature.data is exactly those domain-separated UTF-8 bytes, not JSON alone. Hash them once with SHA-256 before ECDSA, under /43 protocol [2,"p nosend lifecycle"], "1", "anyone". The carrier is exactly {statement, signer, signature}, with a lowercase compressed identity key and strict-DER signature hex; both valid S forms are accepted. Verifiers derive that signer's child publicly, as in BRC-207's attestation construction. The signing identity is the wallet responsible for the root's lifecycle.

This reserved BRC-98 protocol belongs to the nosend module. A supporting wallet MUST keep its keys and linkages internal and permit createSignature only for this exact statement about its own persisted root, matching every fact; hashToDirectlySign and other signing data are rejected. Reject auxiliary encryption, , private-key/linkage disclosure and arbitrary signing through this namespace. Public verification requires no signing permission. Wallet delivery adapters can construct the statement from authoritative storage; the existing action response shape is unchanged. Generic protocol permission cannot authorize arbitrary statements.

Persist the statement and its signature before handoff. Forward original statements for every unresolved protected root when extending a graph; a recipient cannot rewrite a prior wallet's promise under its own identity. Validate signatures, chain, root/anchor dependencies and consistent policy before relying on them. The recipient's delivery/counterparty policy must accept the responsible identity's promise; presence alone is not trust. A lifecycle statement is not an , proof of current root unspentness, proof of the signer's implementation, or an on-chain restriction. An unknown upstream policy MUST be disclosed as unknown, never inferred as never. A known protected root with missing required lifecycle evidence fails protected delivery. Conflicting statements fail rather than selecting the later or more favorable one. Accepted roots retain their historical statements but no longer have a pending finite reclamation deadline.

Capability and compatibility

The optional BRC-205 attribute brc177-nosend=2 advertises this revision, including batches and never. Its absence does not prove non-support; actual requests still require authoritative lifecycle support and authorization. Older implementations reject the new forms. Existing finite single-action labels retain their meaning. BRC-100 signatures, call codes and result shapes are unchanged.

Security Considerations

  • Race at expiry: This mechanism cannot guarantee that a reclaim transaction wins against a concurrent external broadcast. Only the transaction actually mined determines which spend is valid.
  • Observation gaps: A recipient may have broadcast through a service the wallet has not yet observed. Applications should use a safety margin and, where useful, communicate processor acceptance through their own protocol.
  • Clock integrity: A manipulated or badly skewed clock can trigger timestamp expiry early or late. Block height avoids wall-clock dependence but remains subject to ordinary chain reorganizations.
  • Fee changes: The anchor must remain economical to reclaim under plausible fee conditions. Wallets should include a conservative reclaim-fee allowance and keep retrying transient failures.
  • Reservation recovery: Clearing only local spentBy or equivalent state does not invalidate valid transaction bytes held elsewhere. Released finite roots require an actual anchor spend; cancelling a child cannot revoke an exposed ancestor. Released never roots cannot be reclaimed.
  • Bounded exposure: Prefunding limits the reserved wallet value to the action's intended value and fees. Caller-supplied inputs remain governed by their own owners and are not recovered by spending the anchor.
  • No on-chain expiry claim: The label is a wallet instruction, not a script condition, miner rule, or consensus timestamp.

Example Flow

An application requests a five-minute protected action with:

{
  "description": "Offer valid for five minutes",
  "outputs": [
    {
      "satoshis": 1000,
      "lockingScript": "...",
      "outputDescription": "Offer payment"
    }
  ],
  "labels": ["p nosend expiry seconds 300", "offer 42"],
  "options": { "noSend": true }
}

The wallet accepts dedicated funding, returns the protected action and persists its absolute deadline. It does not publish unless explicitly asked through sendWith; the recipient may instead publish before the deadline.

If the recipient broadcasts the action and the wallet observes acceptance within five minutes, normal proof tracking takes over. Otherwise the wallet spends the anchor to a fresh default output. Once that reclaim is mined, the recipient's transaction can no longer be valid on the same chain.

Conformance cases

Request or eventRequired behavior
p nosend expiry never, noSend:trueIsolate funding, persist release, debit as sent; no automatic publication or reclaim.
Unknown never 0, duplicate expiry, unsupported batch modeReject before funding; never substitute another mode.
Two noSend children spend one staged outputReject the second spend, preserving the first exposure.
Batch root has a 500-satoshi approved budgetInternal fee remainder stays within that budget; unrelated change is released before protection.
Token surplus would remain hostage to an offline paymentPrepare an admitted split first or reject; do not hide the encumbrance.
Child joins two finite roots with different deadlinesPreserve both; fail when either still-applicable deadline predicate is met, including mixed height/time predicates.
Child claims never but an ancestor is reclaimableReject that claim; an inherited mixed-policy child must disclose its effective restrictions.
signAction completes a protected childPersist exact signed bytes and exposure; do not broadcast.
Explicit sendWith names the Validate and process its unpublished ancestor closure, returning the ordinary result for the named leaf.
Root accepted, child rejectedCancel root reclaim, retain the child failure and retry/reconcile; never claim atomic rollback.
Delayed request reaches its finite deadline before first submissionReconcile, then expire/reclaim as applicable; queuing did not satisfy the deadline.
Sender disconnects after online prefundingConstruct only with adequate local evidence and durable authoritative reservations; no assumed remote success.
Restart or reservation lease expires after signed handoffRestore protected exposure; never make those inputs available merely due to expiry of a storage lease.
Finite root reclaim winsInvalidate its dependent graph and reconcile separately reserved assets; no claim that their value was itself recovered.
Released never action is abortedExplicit failure, unchanged permanent debit/exposure, no reclaim.
Portable lifecycle statementAuthenticate the responsible wallet, exact root, anchor, network and persisted absolute policy; retain and forward its original signature.
Edited deadline, wrong key or missing protected-root statementFail protected delivery; no invented never promise.
Lost response after batch submissionQuery/reconcile exact TXIDs and retry idempotently; do not create replacement payments.

References

Was this helpful?

Search Beersy

Search standards by number, title, author or topic