6.8 KiB
solana-transaction-awaiting Specification
Purpose
Defines how callers await a definitive Solana transaction outcome at an explicitly requested commitment without resubmitting the transaction.
Requirements
Requirement: Separate transaction awaiting API
The Solana blockchain API SHALL expose a blocking operation that accepts an existing 64-byte Base58 transaction signature, a requested commitment of PROCESSED, CONFIRMED, or FINALIZED, and a strictly positive overall timeout. Submission and awaiting SHALL remain separate operations, and existing consumers SHALL NOT begin awaiting automatically.
Scenario: Valid await request
- WHEN a caller supplies a valid signature, non-null commitment, and positive timeout
- THEN the service observes that already submitted transaction without submitting or resubmitting it
Scenario: Invalid arguments
- WHEN the signature is null, blank, invalid Base58, or does not decode to exactly 64 bytes, the commitment is null, or the timeout is null, zero, or negative
- THEN the service rejects the call locally before making an RPC request
Requirement: Commitment-aware definitive outcomes
The commitment order SHALL be PROCESSED < CONFIRMED < FINALIZED, and an observed level SHALL satisfy the same or any lower requested level. The service SHALL return SUCCEEDED or FAILED only after the observed transaction has reached or exceeded the requested commitment. FAILED SHALL exclusively represent a non-null Solana on-chain err; lower-commitment success or error observations SHALL remain inconclusive.
Scenario: Success reaches requested commitment
- WHEN the transaction is observed at or above the requested commitment with
err: null - THEN the service returns
SUCCEEDEDwith the transaction slot and no failure details
Scenario: Failure reaches requested commitment
- WHEN the transaction is observed at or above the requested commitment with a non-null
err - THEN the service returns
FAILEDwith the transaction slot and the completeerrvalue as compact JSON
Scenario: Observation is below requested commitment
- WHEN a successful or failed transaction is observed below the requested commitment
- THEN the service continues polling rather than returning a definitive outcome
Requirement: Transaction outcome invariants
Every public transaction outcome SHALL enforce that SUCCEEDED has a non-null slot and null failure details, FAILED has a non-null slot and non-blank failure details, and TIMED_OUT has null slot and null failure details.
Scenario: Invalid outcome construction
- WHEN an outcome is constructed with fields inconsistent with its status
- THEN construction fails immediately
Requirement: Signature status polling contract
The service SHALL poll HTTP JSON-RPC getSignatureStatuses with exactly the supplied signature and searchTransactionHistory: true. It SHALL use only result.value[0].slot, err, and confirmationStatus; a null sole value SHALL remain inconclusive. A present status SHALL contain a Long-representable slot and one of processed, confirmed, or finalized.
Scenario: Signature is not found yet
- WHEN
result.valuecontains exactly one null element - THEN the service continues polling until a definitive outcome or timeout
Scenario: Valid status is observed
- WHEN the sole status contains a valid slot, recognized confirmation status, and
errvalue - THEN the service evaluates it against the requested commitment
Requirement: Overall monotonic deadline
The timeout SHALL define one monotonic deadline covering RPC-gate acquisition, shared throttling, HTTP calls, response processing, and subsequent polls. Gate and throttle waiting SHALL be interruptible and deadline-aware, no request SHALL start after the deadline, and an HTTP request SHALL as far as reasonably possible be bounded by the remaining time.
Scenario: Deadline expires before RPC access
- WHEN the deadline expires while waiting for the shared gate or remaining throttle interval
- THEN the service returns
TIMED_OUTwithout starting another RPC request
Scenario: Deadline expires during HTTP request
- WHEN the deadline-bound status HTTP request times out
- THEN the service returns
TIMED_OUT
Scenario: Caller is interrupted
- WHEN interruption occurs during gate acquisition, throttling, HTTP communication, or another internal wait
- THEN
InterruptedExceptionpropagates directly and no subsequent request is made
Requirement: Unknown timeout semantics
TIMED_OUT SHALL mean the requested definitive outcome remains unknown and SHALL NOT imply rejection, failure, expiration, or permission to resubmit. It SHALL not retain a slot previously observed below the requested commitment.
Scenario: Deadline passes without definitive outcome
- WHEN the signature remains unseen or below the requested commitment until the deadline
- THEN the service returns
TIMED_OUTwith null slot and null failure details and does not resubmit the transaction
Requirement: Shared RPC throttling
Status polling SHALL reuse the same shared mechanism that preserves at least five seconds between Solana RPC calls. It SHALL add no independent polling sleep, interval, or limiter, and existing RPC operations SHALL preserve their public behavior and common throttling.
Scenario: Inconclusive poll
- WHEN a status response is inconclusive and time remains
- THEN the next poll is naturally delayed by the shared five-second RPC throttle only
Requirement: Communication and protocol errors
Non-success HTTP responses, JSON-RPC errors, invalid JSON, missing or invalid result.value, arrays with other than exactly one element, invalid slots, missing or unknown confirmation status, and other network or protocol failures SHALL result in IOException, not FAILED. Error messages SHALL identify getSignatureStatuses and include relevant context. The service SHALL NOT automatically retry after an IOException.
Scenario: Invalid RPC response
- WHEN a status response violates the required HTTP, JSON-RPC, result-array, slot, or confirmation-status contract
- THEN the service throws a contextual
IOException
Scenario: Communication failure
- WHEN status communication fails for a reason other than expiration of the overall deadline or thread interruption
- THEN the service throws
IOExceptionwithout automatically polling again
Requirement: Cached decorator delegates directly
The cached Solana blockchain decorator SHALL delegate every transaction-await call directly to its underlying blockchain without caching, reuse, or deduplication.
Scenario: Repeated awaits through cached decorator
- WHEN callers invoke transaction awaiting multiple times through the cached decorator
- THEN every invocation reaches the delegate independently