Using Solana Trackers Standalone
While the Pulsar suite offers a full stack solution with a UI (@tuwaio/nova-transactions) and a Zustand-based state store (@tuwaio/pulsar-core), its architecture remains modular and flexible. This means you can utilize the low-level trackers (solanaFetcher) from @tuwaio/pulsar-solana directly, without installing or configuring the complete state management store.
This flexibility is ideal if:
- You already have your own state management solution (Redux, MobX, Valtio, etc.) and want to integrate only the transaction tracking logic.
- You require tracking on the server-side, where a client-centric store isn’t necessary.
- You desire granular control over each stage of a transaction’s lifecycle for custom workflows.
Why Use solanaFetcher?
Some might ask, “Why should I use solanaFetcher when I can just manually track the transaction state using the Solana RPC?” While manual polling is possible, solanaFetcher provides a more robust, comprehensive, and ready-to-use solution.
| Feature | Solana RPC (manual polling) | solanaFetcher (Pulsar) |
|---|---|---|
| Handles RPC Lags | ❌ No. If called immediately after submission, the RPC node might not have indexed the transaction yet, causing errors. | ✅ Yes. Built-in retry mechanism to wait for the transaction to appear on-chain, mitigating RPC delays. |
| Full Lifecycle Support | 🤷♂️ Limited. You must manually implement logic for different states (sent, confirmed, failed). | ✅ Yes. Provides callbacks for each stage: initialization, details fetched, mined, replaced, failed, etc. |
| Fetches Full Tx Details | ❌ No. Requires additional RPC calls to get full transaction info after confirmation. | ✅ Yes. Calls for getTransaction internally, providing parsed transaction details to callbacks. |
| Abstraction Level | Low. You must manage the tracking states and polling manually. | High. Encapsulates the entire process into a single, convenient async function, simplifying implementation. |
In essence, solanaFetcher is a reliable wrapper around Solana RPC functions, addressing common edge cases and significantly reducing manual effort.
Trackers Overview
1. Solana Tracker
This is the primary tracker for monitoring standard transactions on Solana, identified via a transaction signature. It is designed to be used with the initializePollingTracker from @tuwaio/pulsar-core.
How It Works
solanaFetcher initially attempts to fetch transaction signature status. If the transaction is not found (due to RPC indexing lag), it retries until it is found or a timeout occurs. Once found, it continues to poll until the transaction is finalized. It also fetches full transaction details once they become available.
Example Usage
import { initializePollingTracker } from '@tuwaio/pulsar-core';
import { solanaFetcher } from '@tuwaio/pulsar-solana';
import { OrbitAdapter } from '@tuwaio/orbit-core';
async function trackMySolanaTransaction(txSignature: string, rpcUrl: string, chainId: string) {
await initializePollingTracker({
tx: {
txKey: txSignature,
rpcUrl: rpcUrl,
chainId: chainId, // e.g., 'solana:mainnet' or 'solana:devnet'
adapter: OrbitAdapter.SOLANA,
localTimestamp: Math.floor(Date.now() / 1000),
},
fetcher: solanaFetcher,
onIntervalTick: (response) => {
console.log('Transaction status update:', response);
// response includes slot, confirmations, confirmationStatus, etc.
},
onSuccess: (response) => {
console.log('Transaction finalized!', response);
},
onFailure: (response) => {
console.error('Tracking failed or transaction error:', response?.err);
},
});
}Helper Functions
signAndSendSolanaTx
This utility function simplifies the process of creating, signing, and broadcasting a Solana transaction to the network. It fetches the latest blockhash, creates a versioned transaction (v0), signs it with the provided signer, and sends it.
Example Usage
import type { Instruction, SolanaClient, TransactionSendingSigner } from 'gill';
import { signAndSendSolanaTx } from '@tuwaio/pulsar-solana';
async function sendTransaction(client: SolanaClient, signer: TransactionSendingSigner, instruction: Instruction | Instruction[]) {
try {
const signature = await signAndSendSolanaTx({
client,
signer,
instruction,
});
console.log('Transaction sent with signature:', signature);
return signature;
} catch (error) {
console.error('Failed to send transaction:', error);
}
}checkSolanaChain
This function verifies if the user is connected to the correct Solana network. It compares the required chain identifier with the current one and throws a SolanaChainMismatchError if they don’t match.
Example Usage
import { checkSolanaChain } from '@tuwaio/pulsar-solana';
async function ensureCorrectNetwork(requiredChain: string, currentChain: string) {
try {
checkSolanaChain(requiredChain, currentChain);
console.log('Network is correct, proceeding...');
} catch (error) {
console.error('Network mismatch:', error.message);
}
}Feel free to ask for further customization examples or clarifications on implementing specific trackers or utilities!