curl --request POST \
--url https://public-api.birdeye.so/token/v1/holder/batch \
--header 'Content-Type: application/json' \
--header 'X-API-KEY: <api-key>' \
--data '
{
"token_address": "So11111111111111111111111111111111111111112",
"wallets": [
"5Q544fKrFoe6tsEbD7S8EmxGTJYAKtTVhAW5Q5pge4j1",
"2fgUSSpZFi8PjyhbrETSeLutJpFsuCfWsk2H6gb3Reye",
"CZY9M9BywshFAFjPw7uLgXw9yGtNL26YypLCJdewiHo"
]
}
'import requests
url = "https://public-api.birdeye.so/token/v1/holder/batch"
payload = {
"token_address": "So11111111111111111111111111111111111111112",
"wallets": ["5Q544fKrFoe6tsEbD7S8EmxGTJYAKtTVhAW5Q5pge4j1", "2fgUSSpZFi8PjyhbrETSeLutJpFsuCfWsk2H6gb3Reye", "CZY9M9BywshFAFjPw7uLgXw9yGtNL26YypLCJdewiHo"]
}
headers = {
"X-API-KEY": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'X-API-KEY': '<api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
token_address: 'So11111111111111111111111111111111111111112',
wallets: [
'5Q544fKrFoe6tsEbD7S8EmxGTJYAKtTVhAW5Q5pge4j1',
'2fgUSSpZFi8PjyhbrETSeLutJpFsuCfWsk2H6gb3Reye',
'CZY9M9BywshFAFjPw7uLgXw9yGtNL26YypLCJdewiHo'
]
})
};
fetch('https://public-api.birdeye.so/token/v1/holder/batch', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));{
"data": {
"items": [
{
"balance": "2039280",
"decimals": 9,
"mint": "So11111111111111111111111111111111111111112",
"owner": "2fgUSSpZFi8PjyhbrETSeLutJpFsuCfWsk2H6gb3Reye",
"amount": 0.00203928
},
{
"balance": "1563400084419",
"decimals": 9,
"mint": "So11111111111111111111111111111111111111112",
"owner": "CZY9M9BywshFAFjPw7uLgXw9yGtNL26YypLCJdewiHo",
"amount": 1563.400084419
},
{
"balance": "4961135742857367",
"decimals": 9,
"mint": "So11111111111111111111111111111111111111112",
"owner": "5Q544fKrFoe6tsEbD7S8EmxGTJYAKtTVhAW5Q5pge4j1",
"amount": 4961135.742857367
}
]
},
"success": true
}{
"success": false,
"message": "Bad request"
}{
"success": false,
"message": "Unauthorized"
}{
"success": false,
"message": "Access Denied"
}{
"success": false,
"message": "Too many requests"
}{
"success": false,
"message": "Internal Server Error"
}Token - Holder (Batch)
Retrieve the token balance held by a list of wallet owners.
curl --request POST \
--url https://public-api.birdeye.so/token/v1/holder/batch \
--header 'Content-Type: application/json' \
--header 'X-API-KEY: <api-key>' \
--data '
{
"token_address": "So11111111111111111111111111111111111111112",
"wallets": [
"5Q544fKrFoe6tsEbD7S8EmxGTJYAKtTVhAW5Q5pge4j1",
"2fgUSSpZFi8PjyhbrETSeLutJpFsuCfWsk2H6gb3Reye",
"CZY9M9BywshFAFjPw7uLgXw9yGtNL26YypLCJdewiHo"
]
}
'import requests
url = "https://public-api.birdeye.so/token/v1/holder/batch"
payload = {
"token_address": "So11111111111111111111111111111111111111112",
"wallets": ["5Q544fKrFoe6tsEbD7S8EmxGTJYAKtTVhAW5Q5pge4j1", "2fgUSSpZFi8PjyhbrETSeLutJpFsuCfWsk2H6gb3Reye", "CZY9M9BywshFAFjPw7uLgXw9yGtNL26YypLCJdewiHo"]
}
headers = {
"X-API-KEY": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'X-API-KEY': '<api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
token_address: 'So11111111111111111111111111111111111111112',
wallets: [
'5Q544fKrFoe6tsEbD7S8EmxGTJYAKtTVhAW5Q5pge4j1',
'2fgUSSpZFi8PjyhbrETSeLutJpFsuCfWsk2H6gb3Reye',
'CZY9M9BywshFAFjPw7uLgXw9yGtNL26YypLCJdewiHo'
]
})
};
fetch('https://public-api.birdeye.so/token/v1/holder/batch', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));{
"data": {
"items": [
{
"balance": "2039280",
"decimals": 9,
"mint": "So11111111111111111111111111111111111111112",
"owner": "2fgUSSpZFi8PjyhbrETSeLutJpFsuCfWsk2H6gb3Reye",
"amount": 0.00203928
},
{
"balance": "1563400084419",
"decimals": 9,
"mint": "So11111111111111111111111111111111111111112",
"owner": "CZY9M9BywshFAFjPw7uLgXw9yGtNL26YypLCJdewiHo",
"amount": 1563.400084419
},
{
"balance": "4961135742857367",
"decimals": 9,
"mint": "So11111111111111111111111111111111111111112",
"owner": "5Q544fKrFoe6tsEbD7S8EmxGTJYAKtTVhAW5Q5pge4j1",
"amount": 4961135.742857367
}
]
},
"success": true
}{
"success": false,
"message": "Bad request"
}{
"success": false,
"message": "Unauthorized"
}{
"success": false,
"message": "Access Denied"
}{
"success": false,
"message": "Too many requests"
}{
"success": false,
"message": "Internal Server Error"
}- Usage Note
- Accessibility
- Chain Supported
Check one token across many wallet owners.
- Request body accepts
token_addressandwallets. walletsmust contain 1 to 500 wallet addresses.- Response returns balance rows for wallets that hold the requested token.
ui_amount_mode=scaledapplies Solana Token-2022 scaled UI amount when the token supports scaled UI amount extension.
Reading the numbers. balance is the raw token balance before decimals. amount is the balance after decimals or Token-2022 scaled UI amount when requested and supported.
- Premium
- Business
- Enterprise
Solana
Compute Unit ⚙️
Compute Unit ⚙️
- Batch CU is calculated as
ceil(30 * wallet_count^0.8).
Use Cases 💡
Use Cases 💡
- Check whether a curated wallet list holds a specific token without calling the single-holder endpoint repeatedly.
- Power holder verification workflows for watchlists, KOL wallets, smart wallets, or internal risk lists.
- Enrich wallet cohorts with token balances before ranking exposure or deciding who to monitor.
- Build batch screens that compare which tracked wallets accumulated or still hold a token.
How to Use 🛠️
How to Use 🛠️
- Send a JSON body with
token_addressand awalletsarray. - Keep each request between 1 and 500 wallet addresses.
- Set
ui_amount_mode=rawfor raw decimal-adjusted amounts, orui_amount_mode=scaledfor Solana Token-2022 scaled UI amounts when supported. - Match each returned
ownerback to your submitted wallet list.
Best Practices ✅
Best Practices ✅
- Use batch holder checks when the wallet list is already known; use top-holder APIs when you need to discover holders.
- Deduplicate wallet addresses before calling the API to avoid wasted request size.
- Store zero or missing holders separately if your workflow needs to track wallets that do not currently hold the token.
- Pair batch balances with wallet PnL or transfer APIs when you need behavior, not just current exposure.
Limitations ⚠️
Limitations ⚠️
- Solana only.
- Requires Premium, Business, or Enterprise access.
- This endpoint checks one token per request; it is not a multi-token balance endpoint.
- Response includes current balances, not historical balance changes.
Authorizations
API key for authentication
Headers
Solana network only.
solana Query Parameters
Indicate whether to use the scaled amount for scaled ui amount tokens. Only support solana
raw, scaled Body
Request body for retrieving one token balance across multiple wallet owners.
Wallet owner addresses to check. Supports 1 to 500 wallets per request.
Wallet owner address.
[
"5Q544fKrFoe6tsEbD7S8EmxGTJYAKtTVhAW5Q5pge4j1",
"2fgUSSpZFi8PjyhbrETSeLutJpFsuCfWsk2H6gb3Reye"
]
Token mint address to check in each wallet.
"So11111111111111111111111111111111111111112"
Was this page helpful?

