Solana RPC
Endpoints, request format, limits and method availability for the constant-k Solana JSON-RPC API.
constant-k serves the standard Solana JSON-RPC API from mainnet nodes it builds and runs. Any Solana SDK works unchanged against a constant-k endpoint with your API key.
- Standard JSON-RPC methods, including
getTransaction,getSignaturesForAddressandgetBlock. - Accounts indexed by program ID and by SPL token mint and owner, so queries such as
getTokenAccountsByOwnerresolve from an index. sendTransactionforwards to the next five leaders and rebroadcasts. See Sending Transactions.- WebSocket subscriptions from the Operator plan up. See WebSockets.
Endpoints
https://rpc-newyork.constant-k.com/?api-key=YOUR_API_KEY
https://rpc-frankfurt.constant-k.com/?api-key=YOUR_API_KEY
https://rpc-amsterdam.constant-k.com/?api-key=YOUR_API_KEY
https://rpc.constant-k.com/?api-key=YOUR_API_KEY # nearest regionThe key can also go in a header. See Authentication.
Request format
Requests are JSON-RPC 2.0 over HTTP POST, one call per request. This example reads a wallet's SOL balance.
curl "https://rpc-newyork.constant-k.com/?api-key=YOUR_API_KEY" \
-X POST \
-H "Content-Type: application/json" \
-d '{
"jsonrpc": "2.0",
"id": 1,
"method": "getBalance",
"params": ["83astBRguLMdt2h5U1Tpdq5tjFoJ6noeGwaY3mDLVcri", {"commitment": "confirmed"}]
}'Each method's parameters and response format are in the method reference, for example getBalance, getAccountInfo and getTransaction.
A response can carry HTTP 200 and a JSON-RPC error object. Any body with an error field is a failure, whatever the status code. See Errors.
Commitment levels
Most read methods take a commitment option. It sets how final the data must be.
| Level | Meaning | Suits |
|---|---|---|
processed | The node has processed the block. It can still be skipped. | The lowest latency, when you can handle rollbacks |
confirmed | A supermajority of stake has voted on the block. | Most apps and trading logic |
finalized | The block is rooted and will not change. | Balances you report to users, accounting, withdrawals |
Method availability
Most methods are on every plan. Per-plan rates are on Plans & Limits.
| Methods | Plan |
|---|---|
getLatestBlockhash, getMultipleAccounts, getSignatureStatuses, getSignaturesForAddress, getTokenAccountsByOwner, the staked (SWQoS) send path | Operator and up |
getBlocks, getBlocksWithLimit, getSupply, getTokenLargestAccounts, getProgramAccounts, getProgramAccountsV2, Address Lookup Table lookups | Blade Runner and up |
getProgramAccounts, getProgramAccountsV2 and Address Lookup Table lookups have extra conditions:
getProgramAccountsneeds at least one filter (dataSizeormemcmp). Scans of the token programs must be owner-scoped: adataSize: 165filter plus amemcmpof the full 32-byte owner at offset 32. It runs at 2 calls per second on Blade Runner and 5 on Nexus. Each API key can have 1 call open at a time on Blade Runner and 3 on Nexus, counted together withgetProgramAccountsV2. Over that, the endpoint returns429.getProgramAccountsV2is paginated and returns up to 10,000 accounts per page, 1,000 by default, at 2 calls per second on Blade Runner and 5 on Nexus.- Address Lookup Table lookups are served from an index at 2 calls per second on Blade Runner and 5 on Nexus, through
getProgramAccountsorgetProgramAccountsV2with the ALT program id as the first parameter. There is no separate method or hostname.
Methods not served on any plan
| Method | Instead |
|---|---|
| Batch requests (a JSON array of calls) | One call per HTTP request, in parallel if needed |
getLargestAccounts | Not available |
sendBundle | Single transactions with sendTransaction |
A batch is any JSON array body, including an array with one call in it. It is rejected with HTTP 400 before it reaches a node.
Request limits
| Cap | Value |
|---|---|
| Calls per request | One. A JSON array is rejected. |
| Request body | 1 MB. Over that the gateway returns a plain HTTP 413. The nodes themselves accept 200 KB, so that is the effective ceiling. |
getMultipleAccounts, getSignatureStatuses | 100 items per call |
| Time per request | 60 seconds. A longer call is cut off, so heavy getBlock and getProgramAccounts calls need narrowing. |
Cached reads
Reads can be up to one slot old. Identical getAccountInfo, getMultipleAccounts, getTokenAccountsByOwner, getLatestBlockhash, getSignaturesForAddress, getRecentPrioritizationFees and getSlotLeaders calls that arrive within 366 ms of each other, which is one slot, share a single answer.
Polling the same account faster than that returns the same data and still uses your quota. A getTransaction for a transaction that has not landed is never cached, so confirmation polling always reads live state.
Transaction history
History is served from each region's own ledger. Once a slot falls out of a region's ledger, getTransaction and getSignaturesForAddress can no longer return it.
Cube Runner answers every getBlock request and can return blocks older than the ledger window. On every plan, it returns an older block when the region cache or another region's cache holds that block. On Blade Runner and Nexus tier plans, it also retrieves older blocks from long-term storage, which holds every block since genesis.
- The window is finite and moves with the chain. It is measured in stored data, not in hours, so its length changes with the size of recent blocks.
- The window differs between regions. A signature that resolves in one region can be missing in another. Only the region being queried can answer for its own window.
getFirstAvailableBlockreturns the oldest block from which every later block can be retrieved withgetBlock. On Blade Runner and Nexus tier plans, it returns0, the genesis block. On Free and Operator tier plans, it returns the oldest block from which the region holds every later block, in its cache or its ledger. Older blocks are still returned when a cache in any region holds them.minimumLedgerSlotreturns the oldest slot the region's ledger holds. That slot is the history depth forgetTransactionandgetSignaturesForAddress.- Both calls are cheap and report the actual depth rather than an assumed one.
Transaction and signature history older than the window has to come from your own store, written as the data arrives, or from an archive service.
Browser requests
The endpoints answer CORS preflight requests and allow any origin, including credentials. They accept the X-API-Key and solana-client request headers, so a page can call the RPC directly.
A browser call exposes your API key
Anyone who loads the page can read the key. A public site needs its own backend in front.
Efficient calls
- One HTTP client with keep-alive per process. A new TLS handshake on every call adds a full round trip or more.
- One
getMultipleAccountscall fetches up to 100 accounts, in place of manygetAccountInfocalls. encoding: "base64"withdataSlicereturns only the bytes you need.minContextSlotrejects state older than a slot you have already seen.- A WebSocket subscription or a Kaldera stream replaces fast polling.
- One region per flow. See Choosing a region.