Skip to content
Crypto-only, prepaid. Top up a balance and we draw from it monthly — nothing is ever charged automatically.
tcggraph

REST reference

The primary interface. Predictable URLs, plain JSON, and one filter grammar that works the same way for every game.

Base URL

https://api.tcggraph.com/v1

The API is versioned by date. The current version is 2026-08-01, pinned per key and overridable with the TCGGraph-Version header. Breaking changes never land on an existing version.

Endpoints

MethodPathDescription
GET/v1/gamesList every supported game with counts and metadata.
GET/v1/games/{slug}Retrieve one game, including its schema declaration.
GET/v1/setsList sets, filterable by game, series and release window.
GET/v1/sets/{code}Retrieve one set and its card list.
GET/v1/cardsQuery cards with cross-game and game-specific filters.
GET/v1/cards/{id}Retrieve a single card with all printings.
GET/v1/cards/searchFull-text and fuzzy search across all games.
GET/v1/prices/{cardId}Current prices across every tracked marketplace.
GET/v1/prices/{cardId}/historyDaily price history with range and interval.
POST/v1/bulk/exportsRequest a full-catalog export in JSON, NDJSON or Parquet.
POST/v1/webhooksRegister a signed webhook endpoint.

Filtering

Filters are query parameters. Anything that is not a reserved parameter is matched against gameData, so game-specific filters need no special syntax.

# Cross-game filters
?game=pokemon              # restrict to one game
?name=charizard            # case-insensitive substring
?text=discard              # search rules text
?rarity=Rare+Holo          # exact rarity match
?set=151                   # set code or name
?artist=miki+kudo          # illustrator
?minPrice=50&maxPrice=500  # market price band
?source=cardmarket         # price filters read the EU market, in EUR
?region=EU                 # same thing, without naming a vendor

# Game-specific filters map straight onto gameData
?game=pokemon&hp=330&types=Fire
?game=yugioh&attribute=LIGHT&atk=3000
?game=disney-lorcana&ink=AMETHYST&inkable=false

Every card returns every quote it has regardless of source. What that parameter changes is which quote the price filters and the price sort read from, and the bounds are in that source’s currency — source=cardmarket&minPrice=50 means €50, not $50. The price reference covers both markets in full.

Pagination and sorting

?page=2&limit=50        # limit maxes out at 100
?sort=-price            # name, price, released; prefix - to reverse

Response shape

{
  "data": [ /* Card objects */ ],
  "meta": {
    "page": 1,
    "limit": 20,
    "totalCount": 137,
    "totalPages": 7,
    "hasMore": true,
    "priceSource": "tcgplayer"
  }
}

meta.priceSource echoes back which market the price filters ran against, which is worth asserting on in tests. A USD sort when you meant a EUR one surfaces as a mildly wrong list rather than an error.

Core card fields

Present on every card in every game.

FieldTypeDescription
idStringGlobally unique, stable card identifier.
oracleIdStringGroups every printing and language of the same card.
gameEnumWhich game the card belongs to.
nameStringCard name in the requested language.
normalizedNameStringAccent-folded, lowercased name for fuzzy search.
setObjectSet object: code, name, series, releasedAt, cardCount.
collectorNumberStringNumber printed on the card.
rarityStringPublisher rarity, normalised per game.
rarityRankIntCross-game 0–100 scarcity score for sorting.
artistStringIllustrator credit.
flavorTextStringNon-rules flavour text.
textStringPrimary rules text, plain-text normalised.
languageEnumBCP-47 language code of this printing.
finishes[String]Available finishes for this printing.
imagesObjectsmall, normal, large, png and art-crop URLs on the TCGGraph CDN.
prices[Object]Per-source, per-condition, per-finish pricing with timestamps.
priceHistory[Object]Daily close prices, up to 5 years of history.
legalitiesObjectFormat legality map for the card's game.
externalIdsObjecttcgplayerId, cardmarketId, scryfallId, publisher SKUs and more.
gameDataObjectThe game-specific payload. Typed per game in GraphQL.
updatedAtStringISO-8601 timestamp of the last change to this record.

Game-specific fields

Each game declares its own gameData shape. The per-game reference pages list every field: