Skip to content

JSON-RPC

The JSON-RPC endpoint provides a standard EVM-compatible interface to the Hyperliquid L1 node. Requests are proxied through the Aleatoric gateway with TLS termination, API key authentication, and per-tier rate limiting. The interface conforms to the Ethereum JSON-RPC specification and is compatible with any EVM client library (ethers.js, web3.py, viem, etc.).

RegionURLNotes
US (East US 2)https://rpc.aleatoric.systemsPrimary
JP (Japan East)https://rpc-jp.aleatoric.systemsLive production edge

All requests must be sent as POST with Content-Type: application/json. The US production endpoint is the default North America path. The JP production endpoint is available for approved Japan-region clients and low-latency APAC routing.

Every request must include your API key in the x-api-key HTTP header:

x-api-key: ak_live_your_key_here

Requests without a valid key receive an HTTP 401 response before the JSON-RPC layer processes the payload.

MethodParametersReturnsDescription
eth_blockNumberQUANTITYLatest block number
eth_chainIdQUANTITYChain ID (hex)
eth_getBlockByNumberQUANTITY|TAG, BooleanBlockBlock by number; true for full txs
eth_getBlockByHashDATA(32), BooleanBlockBlock by hash; true for full txs
eth_getBalanceDATA(20), QUANTITY|TAGQUANTITYAccount balance in wei
eth_getTransactionByHashDATA(32)TransactionTransaction by hash
eth_getTransactionReceiptDATA(32)ReceiptReceipt including logs and status
eth_getTransactionCountDATA(20), QUANTITY|TAGQUANTITYNonce for address
eth_callCallObject, QUANTITY|TAGDATAExecute read-only call (no state change)
eth_estimateGasCallObject, QUANTITY|TAGQUANTITYEstimated gas for transaction
eth_getLogsFilterObjectLog[]Event logs matching filter criteria
eth_getCodeDATA(20), QUANTITY|TAGDATAContract bytecode at address
eth_getStorageAtDATA(20), QUANTITY, QUANTITY|TAGDATA(32)Raw storage slot value
net_versionSTRINGNetwork ID

Tag values: "latest", "earliest", "pending". Most queries should use "latest".

Every request is a JSON object with four fields:

{
"jsonrpc": "2.0",
"method": "eth_blockNumber",
"params": [],
"id": 1
}
FieldTypeRequiredDescription
jsonrpcstringYesMust be "2.0"
methodstringYesRPC method name
paramsarrayYesPositional parameters (may be empty)
idinteger|stringYesClient-chosen request identifier, echoed in response

Returns the number of the most recent block.

Terminal window
curl -s -X POST https://rpc.aleatoric.systems \
-H "Content-Type: application/json" \
-H "x-api-key: ak_live_your_key_here" \
-d '{
"jsonrpc": "2.0",
"method": "eth_blockNumber",
"params": [],
"id": 1
}'
{
"jsonrpc": "2.0",
"id": 1,
"result": "0x138e3f0"
}

The result is a hex-encoded block number. In this example, 0x138e3f016=20,570,09610\texttt{0x138e3f0}_{16} = 20,570,096_{10}.

Returns block data. Pass true as the second parameter to include full transaction objects; false for transaction hashes only.

Terminal window
curl -s -X POST https://rpc.aleatoric.systems \
-H "Content-Type: application/json" \
-H "x-api-key: ak_live_your_key_here" \
-d '{
"jsonrpc": "2.0",
"method": "eth_getBlockByNumber",
"params": ["latest", false],
"id": 2
}'
{
"jsonrpc": "2.0",
"id": 2,
"result": {
"number": "0x138e3f0",
"hash": "0x5a2f3c...",
"parentHash": "0x91b8e2...",
"timestamp": "0x65f1a2b0",
"transactions": ["0xabc123...", "0xdef456..."],
"gasUsed": "0x5208",
"gasLimit": "0x1c9c380"
}
}

Query event logs by block range, address, and topic filters. The fromBlock / toBlock range is capped at 10,000 blocks per request.

Terminal window
curl -s -X POST https://rpc.aleatoric.systems \
-H "Content-Type: application/json" \
-H "x-api-key: ak_live_your_key_here" \
-d '{
"jsonrpc": "2.0",
"method": "eth_getLogs",
"params": [{
"fromBlock": "0x138e000",
"toBlock": "0x138e3f0",
"address": "0x1234567890abcdef1234567890abcdef12345678",
"topics": [
"0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef"
]
}],
"id": 3
}'
{
"jsonrpc": "2.0",
"id": 3,
"result": [
{
"address": "0x1234567890abcdef1234567890abcdef12345678",
"topics": [
"0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef",
"0x000000000000000000000000aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
"0x000000000000000000000000bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb"
],
"data": "0x0000000000000000000000000000000000000000000000000de0b6b3a7640000",
"blockNumber": "0x138e100",
"transactionHash": "0xfedcba...",
"logIndex": "0x0"
}
]
}

The topics[0] value above is the ERC-20 Transfer(address,address,uint256) event signature. The data field encodes the transfer amount; here 0xde0b6b3a764000016=1018\texttt{0xde0b6b3a7640000}_{16} = 10^{18} wei = 1 token (assuming 18 decimals).

Execute a read-only contract call. This does not create a transaction or consume gas.

Terminal window
curl -s -X POST https://rpc.aleatoric.systems \
-H "Content-Type: application/json" \
-H "x-api-key: ak_live_your_key_here" \
-d '{
"jsonrpc": "2.0",
"method": "eth_call",
"params": [{
"to": "0x1234567890abcdef1234567890abcdef12345678",
"data": "0x70a08231000000000000000000000000aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"
}, "latest"],
"id": 4
}'
{
"jsonrpc": "2.0",
"id": 4,
"result": "0x0000000000000000000000000000000000000000000000056bc75e2d63100000"
}

The data field contains the ABI-encoded function selector for balanceOf(address) (0x70a08231) followed by the zero-padded address argument.

The endpoint supports batch requests per the JSON-RPC 2.0 specification. Send an array of request objects and receive an array of responses. The maximum batch size is 100 requests.

Terminal window
curl -s -X POST https://rpc.aleatoric.systems \
-H "Content-Type: application/json" \
-H "x-api-key: ak_live_your_key_here" \
-d '[
{"jsonrpc": "2.0", "method": "eth_blockNumber", "params": [], "id": 1},
{"jsonrpc": "2.0", "method": "eth_chainId", "params": [], "id": 2},
{"jsonrpc": "2.0", "method": "eth_getBalance", "params": ["0xaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa", "latest"], "id": 3}
]'
[
{"jsonrpc": "2.0", "id": 1, "result": "0x138e3f0"},
{"jsonrpc": "2.0", "id": 2, "result": "0xa4b1"},
{"jsonrpc": "2.0", "id": 3, "result": "0x56bc75e2d63100000"}
]

Notes on batching:

  • Each request in the batch counts as one request against your rate limit.
  • A batch with n>100n > 100 requests is rejected with a single error response.
  • Responses are returned in the same order as requests.
  • If an individual request within the batch fails, only that entry contains an error object; the rest succeed normally.

Errors follow the JSON-RPC 2.0 error format:

{
"jsonrpc": "2.0",
"id": 1,
"error": {
"code": -32601,
"message": "Method not found"
}
}
CodeMessageDescription
-32700Parse errorInvalid JSON payload
-32600Invalid RequestMissing required fields or wrong jsonrpc version
-32601Method not foundUnknown or unsupported method name
-32602Invalid paramsWrong number or type of parameters
-32603Internal errorServer-side failure

These are returned as HTTP status codes before the JSON-RPC layer:

HTTP StatusCauseResponse Body
401Missing or invalid x-api-key{"error": "Unauthorized"}
429Rate limit exceeded{"error": "Rate limit exceeded", "retry_after_ms": N}
502Upstream node unavailable{"error": "Bad Gateway"}
503Service temporarily unavailable{"error": "Service Unavailable"}

Rate limits are enforced at the Nginx gateway layer per API key.

LimitValue
Global burst cap5,000 req/s per API key
Sustained throughputTier-dependent (see Rate Limits)
Batch countingEach request in a batch counts individually

When a rate limit is hit, the gateway returns HTTP 429 with a retry_after_ms field indicating the minimum backoff in milliseconds. Clients should implement exponential backoff rather than retrying at a fixed interval.

For sustained high-throughput workloads (e.g., block-by-block indexing), consider:

  • Using batch requests to reduce HTTP overhead (up to 100 per batch).
  • Connecting to the regional endpoint closest to your infrastructure.
  • Upgrading to a higher tier if you consistently hit limits.