Cosmos - Fetching All Transactions from an Address
Retrieving all transactions for a Cosmos address is possible through the Tendermint RPC method tx_search.
However, this method is resource-intensive and can lead to long response times if not scoped properly.
This article explains how to use tx_search effectively, why it’s computationally heavy, and how to limit its impact by defining block ranges.
Using tx_search on Cosmos
tx_search allows filtering transactions by event tags such as transfer.recipient or message.sender.
A correct request looks like this:
curl --location 'https://cosmos-mainnet.gateway.tatum.io/tendermint/' \
--header 'Content-Type: application/json' \
--header 'x-api-key: {YOUR_API_KEY}' \
--data '{
"id": 1,
"jsonrpc": "2.0",
"method": "tx_search",
"params": {
"order_by": "desc",
"page": "1",
"per_page": "30",
"query": "transfer.recipient='cosmos1hgp84me0lze8t4jfrwsr05aep2kr57zrk4gecx' AND tx.height>28155409 AND tx.height<28166675"
}
}'
This query fetches up to 30 transactions where the specified address received tokens between block 28155409 and 28166675.
Why the Request Is Heavy
The tx_search RPC endpoint performs a full index lookup in the Tendermint node’s transaction database.
If no block range is specified, the node may need to scan millions of transactions to evaluate event tags like transfer.recipient, causing:
- Very high response time: responses often take 30–60 seconds or longer to direct timeouts
- Increased node load: high I/O and CPU consumption
This behavior is normal for Tendermint RPC; it’s not optimized for high-frequency or large-scale address searches.
Best Practices
- Always define a block range
Restrict the height range to smaller segments, for example:A 5,000–10,000 block window is a good balance between speed and coverage.`"query": "transfer.recipient='cosmos1...' AND tx.height>28100000 AND tx.height<28105000"` - Paginate results
Use"page": "2","page": "3", etc. to iterate through multiple result pages within the range. - Walk the chain incrementally
Automate the process by iterating over consecutive height ranges:
This approach prevents full-chain scans and keeps response times reasonable.28100000–28105000 28105001–28110000 28110001–28115000 ... - Adjust query parameters
- Use
"order_by": "desc"to start from the newest blocks. - Focus on keeping your block range scope narrow. Overly broad height intervals can drastically slow down responses to make requests start timing out.
- Use
Summary
| Approach | Description | Performance |
|---|---|---|
tx_search without block range | Full-chain scan across all transactions | ❌ Very slow (30–60 s+) |
tx_search with block range | Limited height window | ⚠️ Manageable (3–10 s) |
| Iterative height windows | Scripted queries by block segments | ✅ Efficient and scalable |
Updated about 3 hours ago