Documentation
¶
Index ¶
- Constants
- type GaslessTxRequest
- type GaslessTxResponse
- type SolanaVerifier
- func (s *SolanaVerifier) BuildGaslessTransaction(ctx context.Context, req GaslessTxRequest) (GaslessTxResponse, error)
- func (s *SolanaVerifier) Close()
- func (s *SolanaVerifier) EnableAutoCreateTokenAccounts()
- func (s *SolanaVerifier) EnableGasless()
- func (s *SolanaVerifier) GetHealthChecker() *WalletHealthChecker
- func (s *SolanaVerifier) RPCClient() *rpc.Client
- func (s *SolanaVerifier) SetServerWallets(wallets []solana.PrivateKey)
- func (s *SolanaVerifier) SetupTxQueue(minTimeBetween time.Duration, maxInFlight int)
- func (s *SolanaVerifier) ShutdownTxQueue()
- func (s *SolanaVerifier) Verify(ctx context.Context, proof x402.PaymentProof, requirement x402.Requirement) (x402.VerificationResult, error)
- func (s *SolanaVerifier) WithMetrics(m *metrics.Metrics, network string) *SolanaVerifier
- type TransactionQueue
- type WalletHealth
- type WalletHealthChecker
- func (w *WalletHealthChecker) CheckAll()
- func (w *WalletHealthChecker) GetHealth() []WalletHealth
- func (w *WalletHealthChecker) GetHealthyWallet(currentIndex *uint64) *solana.PrivateKey
- func (w *WalletHealthChecker) GetWalletHealth(pubkey solana.PublicKey) (*WalletHealth, bool)
- func (w *WalletHealthChecker) HealthySummary() (healthy, unhealthy, critical int)
- func (w *WalletHealthChecker) SetCriticalCallback(fn func(wallet WalletHealth))
- func (w *WalletHealthChecker) Start()
- func (w *WalletHealthChecker) Stop()
Constants ¶
const ( // MinHealthyBalance is the minimum SOL balance required for a wallet to be considered healthy. // This threshold accounts for: // - Rent-exempt minimum: ~0.00089 SOL for wallet account data // - Token account creation: ~0.002 SOL for recipient token account (if auto-create enabled) // - Transaction fees: ~0.000005 SOL per transaction // At 0.005 SOL, wallet can maintain rent-exemption, create token accounts, and process ~1,000 transactions. MinHealthyBalance = 0.005 // SOL // CriticalBalance is the balance at which we consider the wallet critically low. // Below this threshold, wallet may not have enough for token account creation + rent. CriticalBalance = 0.001 // SOL // HealthCheckInterval is how often we check wallet balances. // More frequent than monitoring (15min) to catch issues faster. HealthCheckInterval = 5 * time.Minute // HealthCheckTimeout is the RPC timeout for balance queries. HealthCheckTimeout = 10 * time.Second )
const ( // QueuePollInterval is how frequently the worker checks for new transactions when queue is empty. QueuePollInterval = 50 * time.Millisecond // TxTimeout is the timeout for sending and confirming individual transactions. TxTimeout = 30 * time.Second // TxConfirmTimeout is the timeout for waiting for transaction confirmation. TxConfirmTimeout = 60 * time.Second // MaxTxRetries is the maximum number of times to retry a rate-limited transaction. MaxTxRetries = 3 )
Variables ¶
This section is empty.
Functions ¶
This section is empty.
Types ¶
type GaslessTxRequest ¶
type GaslessTxRequest struct {
PayerWallet solana.PublicKey // User's wallet (signs transfer, not fees)
FeePayer *solana.PublicKey // Optional: specific server wallet to use as fee payer
RecipientTokenAccount solana.PublicKey // Destination token account
TokenMint solana.PublicKey // Token mint address (e.g., USDC)
Amount uint64 // Amount in atomic units (e.g., lamports for SOL, smallest unit for SPL tokens)
Decimals uint8 // Token decimals (e.g., 6 for USDC)
Memo string // Payment memo
ComputeUnitLimit uint32 // Maximum compute units (e.g., 200000)
ComputeUnitPrice uint64 // Priority fee in microlamports (e.g., 1)
Blockhash solana.Hash // Recent blockhash (should be from cache)
}
GaslessTxRequest contains the parameters needed to build a gasless transaction.
type GaslessTxResponse ¶
type GaslessTxResponse struct {
Transaction string `json:"transaction"` // Base64-encoded unsigned transaction
Blockhash string `json:"blockhash"` // Recent blockhash used
FeePayer string `json:"feePayer"` // Server wallet that will pay fees
}
GaslessTxResponse contains the unsigned transaction to be partially signed by the user.
type SolanaVerifier ¶
type SolanaVerifier struct {
// contains filtered or unexported fields
}
SolanaVerifier confirms x402 payments against the Solana blockchain.
func NewSolanaVerifier ¶
func NewSolanaVerifier(rpcURL, wsURL string) (*SolanaVerifier, error)
NewSolanaVerifier creates a verifier backed by RPC + WebSocket endpoints.
func (*SolanaVerifier) BuildGaslessTransaction ¶
func (s *SolanaVerifier) BuildGaslessTransaction(ctx context.Context, req GaslessTxRequest) (GaslessTxResponse, error)
BuildGaslessTransaction constructs a complete transaction for gasless payments. The transaction includes: 1. Compute budget instructions (unit limit + priority fee) 2. SPL token transfer instruction 3. Memo instruction
The transaction is NOT signed. The frontend should: 1. Deserialize the transaction 2. Have the user sign it (partial signature - transfer authority only) 3. Send the partially signed transaction back to the backend 4. Backend co-signs as fee payer and submits
func (*SolanaVerifier) Close ¶
func (s *SolanaVerifier) Close()
Close releases underlying websocket resources and stops health checker.
func (*SolanaVerifier) EnableAutoCreateTokenAccounts ¶
func (s *SolanaVerifier) EnableAutoCreateTokenAccounts()
EnableAutoCreateTokenAccounts enables automatic token account creation. When enabled, if a payment fails due to a missing token account, the verifier will create it and retry.
func (*SolanaVerifier) EnableGasless ¶
func (s *SolanaVerifier) EnableGasless()
EnableGasless enables gasless transaction support. When enabled, the verifier will co-sign partially signed transactions with a server wallet.
func (*SolanaVerifier) GetHealthChecker ¶
func (s *SolanaVerifier) GetHealthChecker() *WalletHealthChecker
GetHealthChecker returns the wallet health checker for monitoring.
func (*SolanaVerifier) RPCClient ¶
func (s *SolanaVerifier) RPCClient() *rpc.Client
RPCClient returns the underlying RPC client for direct access.
func (*SolanaVerifier) SetServerWallets ¶
func (s *SolanaVerifier) SetServerWallets(wallets []solana.PrivateKey)
SetServerWallets configures the server wallets for gasless transactions and token account creation. Wallets are used in round-robin fashion to distribute load and avoid rate limits. This also initializes and starts the wallet health checker.
func (*SolanaVerifier) SetupTxQueue ¶
func (s *SolanaVerifier) SetupTxQueue(minTimeBetween time.Duration, maxInFlight int)
SetupTxQueue initializes the transaction queue with the given rate limiting settings.
func (*SolanaVerifier) ShutdownTxQueue ¶
func (s *SolanaVerifier) ShutdownTxQueue()
ShutdownTxQueue stops the transaction queue gracefully.
func (*SolanaVerifier) Verify ¶
func (s *SolanaVerifier) Verify(ctx context.Context, proof x402.PaymentProof, requirement x402.Requirement) (x402.VerificationResult, error)
Verify inspects the signed transaction, submits it, and waits for finalised confirmation.
func (*SolanaVerifier) WithMetrics ¶
func (s *SolanaVerifier) WithMetrics(m *metrics.Metrics, network string) *SolanaVerifier
WithMetrics adds metrics collection to the verifier.
type TransactionQueue ¶
type TransactionQueue struct {
// contains filtered or unexported fields
}
TransactionQueue is a simple queue that sends transactions with rate limiting. Rate-limited transactions go back to the TOP of the queue.
func NewTransactionQueue ¶
func NewTransactionQueue(rpcClient *rpc.Client, verifier *SolanaVerifier, minTimeBetween time.Duration, maxInFlight int) *TransactionQueue
NewTransactionQueue creates the queue.
func (*TransactionQueue) Enqueue ¶
func (q *TransactionQueue) Enqueue(id string, tx *solana.Transaction, opts rpc.TransactionOpts, req x402.Requirement)
Enqueue adds a transaction to the queue.
func (*TransactionQueue) EnqueuePriority ¶
func (q *TransactionQueue) EnqueuePriority(qtx *queuedTx)
EnqueuePriority adds a rate-limited transaction to the FRONT of the queue.
func (*TransactionQueue) Start ¶
func (q *TransactionQueue) Start()
Start begins processing the queue.
func (*TransactionQueue) Stats ¶
func (q *TransactionQueue) Stats() map[string]int
Stats returns queue stats.
type WalletHealth ¶
type WalletHealth struct {
PublicKey solana.PublicKey
Balance float64 // Current SOL balance
IsHealthy bool // true if balance >= MinHealthyBalance
IsCritical bool // true if balance <= CriticalBalance
LastChecked time.Time // When balance was last checked
LastCheckError error // Error from last balance check (if any)
}
WalletHealth tracks the health status of a server wallet.
type WalletHealthChecker ¶
type WalletHealthChecker struct {
// contains filtered or unexported fields
}
WalletHealthChecker monitors server wallet balances and tracks health status.
func NewWalletHealthChecker ¶
func NewWalletHealthChecker(rpcClient *rpc.Client, wallets []solana.PrivateKey) *WalletHealthChecker
NewWalletHealthChecker creates a new health checker.
func (*WalletHealthChecker) CheckAll ¶
func (w *WalletHealthChecker) CheckAll()
CheckAll checks the balance of all wallets and updates their health status.
func (*WalletHealthChecker) GetHealth ¶
func (w *WalletHealthChecker) GetHealth() []WalletHealth
GetHealth returns the current health status of all wallets.
func (*WalletHealthChecker) GetHealthyWallet ¶
func (w *WalletHealthChecker) GetHealthyWallet(currentIndex *uint64) *solana.PrivateKey
GetHealthyWallet returns the next healthy wallet using round-robin selection. Returns nil if no healthy wallets are available.
func (*WalletHealthChecker) GetWalletHealth ¶
func (w *WalletHealthChecker) GetWalletHealth(pubkey solana.PublicKey) (*WalletHealth, bool)
GetWalletHealth returns health for a specific wallet.
func (*WalletHealthChecker) HealthySummary ¶
func (w *WalletHealthChecker) HealthySummary() (healthy, unhealthy, critical int)
HealthySummary returns a summary of wallet health.
func (*WalletHealthChecker) SetCriticalCallback ¶
func (w *WalletHealthChecker) SetCriticalCallback(fn func(wallet WalletHealth))
SetCriticalCallback sets a callback to be invoked when a wallet's balance becomes critical.
func (*WalletHealthChecker) Start ¶
func (w *WalletHealthChecker) Start()
Start begins background health checking.
func (*WalletHealthChecker) Stop ¶
func (w *WalletHealthChecker) Stop()
Stop gracefully stops the health checker.