logoPandorLabs
Crypto

OpenSea Collections

NFT collection rankings on OpenSea across every chain — floor price, volume, supply, owners, socials and holders.

opensea-collectionsopenseacryptonftmarketplacerankings

1,000 rows in the dataset

Download the dataset

Get every row this scraper has collected as one CSV or JSONL file. If the data is older than maxAgeHours, the scraper is re-run with its configured settings first. The key needs the datasets:export scope.

DOWNLOAD_ID=$(curl -s -X POST "https://api.pandorlabs.com/v1/datasets/opensea-collections/downloads" \  -H "Authorization: Bearer $PANDORLABS_KEY" \  -H "Content-Type: application/json" \  -d '{"maxAgeHours":24,"format":"csv"}' | jq -r '.id')while true; do  STATUS=$(curl -s "https://api.pandorlabs.com/v1/downloads/$DOWNLOAD_ID" \    -H "Authorization: Bearer $PANDORLABS_KEY" | jq -r '.status')  [ "$STATUS" != "refreshing" ] && break  sleep 5donecurl -s "https://api.pandorlabs.com/v1/downloads/$DOWNLOAD_ID/file" \  -H "Authorization: Bearer $PANDORLABS_KEY" \  -o dataset.csv

At its current 1,000 rows, this download costs 10 credits when the data is fresh enough, or 20 credits when it has to be refreshed first.

The rate is 1 credit per 100 rows cached and 2 credits live, charged on the rows in the dataset when the download becomes ready. A failed refresh is not charged. The file stays downloadable for 24 hours. See pricing.

Start a run

To choose the targets yourself, send the parameters below as input. The call returns 202 with the run; the key needs the scrapers:run scope and the account a positive credit balance.

curl -X POST "https://api.pandorlabs.com/v1/scrapers/opensea-collections/runs" \  -H "Authorization: Bearer $PANDORLABS_KEY" \  -H "Content-Type: application/json" \  -d '{    "input": {      "sortBy": "VOLUME",      "sortDirection": "DESC",      "chains": [        "ethereum"      ],      "category": "PFPS"    }  }'

A run is billed at the live rate once it finishes: 2 credits per 100 rows it collected. A run that collects nothing costs nothing.

Parameters

Every parameter is optional. Anything you leave out uses the default shown here; an unknown name or an invalid value is rejected with a 400 that lists each problem.

Targeting

  • sortBy

    enum

    Rank by

    Which volume window ranks the table. Only the volume family is offered — OpenSea accepts FLOOR_PRICE and SALES and then drops the connection.

    Default
    VOLUME
    Allowed values
    VOLUME
    ONE_MINUTE_VOLUME
    FIVE_MINUTE_VOLUME
    FIFTEEN_MINUTE_VOLUME
    ONE_HOUR_VOLUME
    ONE_DAY_VOLUME
    SEVEN_DAYS_VOLUME
    THIRTY_DAYS_VOLUME
  • sortDirection

    enum

    Direction

    Default
    DESC
    Allowed values
    DESC
    ASC
  • chains

    string[]

    Chains

    Chain slugs — ethereum, solana, base, polygon, hyperevm. Empty collects every chain. An unknown slug fails the whole page, so check spelling.

    Default
    none
    Example
    ethereum
  • category

    string

    Category

    OpenSea's own taxonomy, upper-cased: PFPS, ART, GAMING, … An unrecognised value fails the page rather than being ignored.

    Default
    none
    Example
    PFPS
  • ownerAddress

    string

    Owned by wallet

    Collect only the collections this wallet owns. OpenSea's own filter, so it is exact rather than a search — a wallet nobody matches returns an empty first page, which is warned about.

    Default
    none
    Example
    0x…
  • maxCollections

    number

    Max collections per run

    Ceiling on rows collected. Paging was walked past 25,000 collections without a duplicate or a refusal, so this bounds the run rather than the endpoint. Rows upsert, so it bounds one run rather than the dataset, and a ceiling that truncates the listing is reported as a warning.

    Default
    1000
    Range
    1 to 50000

Holders

  • enrichHolders

    boolean

    Sample holders

    Walk each collection’s tokens and record the wallets behind them, with their OpenSea portfolio value and X handle. Costs one request per 100 tokens.

    Default
    false
  • holderCollections

    string[]

    Sample only these slugs

    Restrict holder sampling to named collections. Empty samples the highest-ranked ones this run collected.

    Default
    none
    Example
    cryptopunks
  • maxHolderCollections

    number

    Max collections sampled

    Default
    10
    Range
    1 to 500
  • holderItemsPerCollection

    number

    Tokens walked per collection

    A sample, not a census: 6,000 tokens of BAYC yielded 3,661 distinct wallets. One request per 100 tokens, and paging held for every one of those 60 pages.

    Default
    500
    Range
    1 to 20000
  • topHoldersKept

    number

    Top holders stored per collection

    Richest first. The counts and the median are computed over the whole sample regardless of this.

    Default
    50
    Range
    1 to 1000
  • holderValueSource

    enum

    Portfolio valuation from

    opensea is free and arrives inline. nftscan needs NFTSCAN_API_KEY and costs one request per wallet; without a key the run fails rather than silently downgrading.

    Default
    opensea
    Allowed values
    opensea
    nftscan
  • nftscanApiKey

    string

    NFTScan API key

    Overrides the NFTSCAN_API_KEY environment variable. Only read when the valuation source is nftscan.

    Default
    none

Advanced

  • collectionsPerPage

    number

    Collections per request

    OpenSea rejects anything above 100.

    Default
    100
    Range
    1 to 100
  • requestDelayMs

    number

    Delay between requests (ms)

    The endpoint reports a 400-request budget in its own response extensions; 500 ms keeps a long run comfortably inside it. 252 consecutive pages at 400 ms drew no refusal on 2026-09-03.

    Default
    500
    Range
    0 to 30000
Input as JSON Schema

The same schema the API validates against. Use it as a tool input schema or to generate a typed client.

inputSchema
{  "type": "object",  "additionalProperties": false,  "properties": {    "sortBy": {      "type": "string",      "enum": [        "VOLUME",        "ONE_MINUTE_VOLUME",        "FIVE_MINUTE_VOLUME",        "FIFTEEN_MINUTE_VOLUME",        "ONE_HOUR_VOLUME",        "ONE_DAY_VOLUME",        "SEVEN_DAYS_VOLUME",        "THIRTY_DAYS_VOLUME"      ],      "title": "Rank by",      "description": "Which volume window ranks the table. Only the volume family is offered — OpenSea accepts FLOOR_PRICE and SALES and then drops the connection.",      "default": "VOLUME"    },    "sortDirection": {      "type": "string",      "enum": [        "DESC",        "ASC"      ],      "title": "Direction",      "default": "DESC"    },    "chains": {      "type": "array",      "items": {        "type": "string"      },      "maxItems": 1000,      "title": "Chains",      "description": "Chain slugs — ethereum, solana, base, polygon, hyperevm. Empty collects every chain. An unknown slug fails the whole page, so check spelling.",      "default": [],      "examples": [        "ethereum"      ]    },    "category": {      "type": "string",      "maxLength": 2000,      "title": "Category",      "description": "OpenSea's own taxonomy, upper-cased: PFPS, ART, GAMING, … An unrecognised value fails the page rather than being ignored.",      "examples": [        "PFPS"      ]    },    "ownerAddress": {      "type": "string",      "maxLength": 2000,      "title": "Owned by wallet",      "description": "Collect only the collections this wallet owns. OpenSea's own filter, so it is exact rather than a search — a wallet nobody matches returns an empty first page, which is warned about.",      "examples": [        "0x…"      ]    },    "maxCollections": {      "type": "number",      "minimum": 1,      "maximum": 50000,      "title": "Max collections per run",      "description": "Ceiling on rows collected. Paging was walked past 25,000 collections without a duplicate or a refusal, so this bounds the run rather than the endpoint. Rows upsert, so it bounds one run rather than the dataset, and a ceiling that truncates the listing is reported as a warning.",      "default": 1000    },    "enrichHolders": {      "type": "boolean",      "title": "Sample holders",      "description": "Walk each collection’s tokens and record the wallets behind them, with their OpenSea portfolio value and X handle. Costs one request per 100 tokens.",      "default": false    },    "holderCollections": {      "type": "array",      "items": {        "type": "string"      },      "maxItems": 1000,      "title": "Sample only these slugs",      "description": "Restrict holder sampling to named collections. Empty samples the highest-ranked ones this run collected.",      "default": [],      "examples": [        "cryptopunks"      ]    },    "maxHolderCollections": {      "type": "number",      "minimum": 1,      "maximum": 500,      "title": "Max collections sampled",      "default": 10    },    "holderItemsPerCollection": {      "type": "number",      "minimum": 1,      "maximum": 20000,      "title": "Tokens walked per collection",      "description": "A sample, not a census: 6,000 tokens of BAYC yielded 3,661 distinct wallets. One request per 100 tokens, and paging held for every one of those 60 pages.",      "default": 500    },    "topHoldersKept": {      "type": "number",      "minimum": 1,      "maximum": 1000,      "title": "Top holders stored per collection",      "description": "Richest first. The counts and the median are computed over the whole sample regardless of this.",      "default": 50    },    "holderValueSource": {      "type": "string",      "enum": [        "opensea",        "nftscan"      ],      "title": "Portfolio valuation from",      "description": "opensea is free and arrives inline. nftscan needs NFTSCAN_API_KEY and costs one request per wallet; without a key the run fails rather than silently downgrading.",      "default": "opensea"    },    "nftscanApiKey": {      "type": "string",      "maxLength": 2000,      "title": "NFTScan API key",      "description": "Overrides the NFTSCAN_API_KEY environment variable. Only read when the valuation source is nftscan."    },    "collectionsPerPage": {      "type": "number",      "minimum": 1,      "maximum": 100,      "title": "Collections per request",      "description": "OpenSea rejects anything above 100.",      "default": 100    },    "requestDelayMs": {      "type": "number",      "minimum": 0,      "maximum": 30000,      "title": "Delay between requests (ms)",      "description": "The endpoint reports a 400-request budget in its own response extensions; 500 ms keeps a long run comfortably inside it. 252 consecutive pages at 400 ms drew no refusal on 2026-09-03.",      "default": 500    }  }}

Run, poll, read rows

The run is asynchronous. Poll it until it reaches a terminal status and its billing is paid, then page through its rows. Until then the rows endpoint answers 409 (still queued or running) or 402 (payment required).

RUN_ID=$(curl -s -X POST "https://api.pandorlabs.com/v1/scrapers/opensea-collections/runs" \  -H "Authorization: Bearer $PANDORLABS_KEY" \  -H "Content-Type: application/json" \  -d '{    "input": {      "sortBy": "VOLUME",      "sortDirection": "DESC",      "chains": [        "ethereum"      ],      "category": "PFPS"    }  }' | jq -r '.id')while true; do  RUN=$(curl -s "https://api.pandorlabs.com/v1/runs/$RUN_ID" \    -H "Authorization: Bearer $PANDORLABS_KEY")  STATUS=$(echo "$RUN" | jq -r '.status')  BILLING=$(echo "$RUN" | jq -r '.billing.status')  case "$STATUS" in queued|running) ;; *) [ "$BILLING" != "pending" ] && break ;; esac  sleep 5doneecho "$RUN" | jq '{status, rowCount, billing}'curl -s "https://api.pandorlabs.com/v1/runs/$RUN_ID/rows?page=1&limit=100" \  -H "Authorization: Bearer $PANDORLABS_KEY"

See the API reference for pagination, cancelling and listing runs.

Output fields

Rows have no fixed schema; these are the fields observed in the rows collected so far. Coverage is the share of rows where the field is present.

FieldTypeCoverage
banner_image_urlstring93%
categorystring100%
chainstring100%
chain_archstring100%
chain_namestring100%
chain_native_symbolstring100%
chain_network_idnumber100%
collection_idstring100%
contract_addressstring100%
creator_fee_basis_pointsnumber100%
creator_fee_requiredboolean100%
descriptionstring94%
discord_urlstring69%
external_urlstring91%
featured_image_urlstring82%
fifteen_minuteobject100%
five_minuteobject100%
floor_price_nativenumber99%
floor_price_symbolstring99%
floor_price_usdnumber99%
floor_sparkline_7darray99%
image_urlstring100%
instagram_usernamestring42%
is_creator_fees_enforcedboolean100%
is_disabledboolean100%
is_item_offers_enabledboolean100%
is_offers_enabledboolean100%
is_rarity_disabledboolean100%
is_verifiedboolean100%
listed_item_countnumber100%
medium_usernamestring17%
metadata_storagestring100%
namestring100%
one_dayobject100%
one_hourobject100%
one_minuteobject100%
owner_addressstring99%
owner_countnumber100%
owner_display_namestring84%
owner_is_verifiedboolean99%
owner_portfolio_usdnumber99%
owner_twitter_usernamestring37%
owner_usernamestring82%
ranknumber100%
sales_totalnumber100%
seven_daysobject100%
slugstring100%
sort_bystring100%
sort_directionstring100%
telegram_urlstring4%
thirty_daysobject100%
token_standardstring100%
top_offer_nativenumber89%
top_offer_symbolstring89%
top_offer_usdnumber89%
total_supplynumber100%
twitter_usernamestring85%
unique_item_countnumber100%
volume_nativenumber100%
volume_symbolstring100%
volume_usdnumber100%
created_atdate100%
first_seen_atdate100%
last_seen_atdate100%
launched_atdate100%
updated_atdate100%
_idstring100%

© 2026 PandorLabs LLC. All rights reserved.