Scryfall LLC · Magic: The Gathering only
Scryfall alternative — when you need more than Magic
Scryfall is the best Magic: The Gathering API there is, and it is free. TCGGraph is what you reach for when your app also needs Pokémon, One Piece or Lorcana behind the same schema and the same key.
What Scryfall does well
- Free, generous and genuinely excellent for Magic. No key required.
- The best full-text search syntax in the hobby, and a huge community around it.
- Complete Oracle text, every printing, every language, plus bulk data dumps.
- Run by people who care deeply about Magic data quality.
Where TCGGraph differs
- Scryfall covers Magic and only Magic, by design. If your product is Magic-only, that is not a limitation.
- TCGGraph carries eight games behind one schema, so adding a second game costs you an enum value rather than a second integration.
- TCGGraph normalises prices across five marketplaces with daily history; Scryfall surfaces marketplace links and current prices.
- TCGGraph offers signed webhooks for set releases, spoilers and legality changes, so you do not have to poll.
Side by side
Feature comparison
| Feature | Scryfall | TCGGraph |
|---|---|---|
| Games covered | Magic only | 8 games |
| Consistent schema across games | ||
| Price history | Current prices | Daily, to 2019 |
| European prices (Cardmarket) | Magic only | All 8 games |
| Normalised multi-marketplace prices | 5 sources | |
| GraphQL | ||
| Webhooks | ||
| Bulk exports | ||
| Image CDN | ||
| Price | Free | From $19/mo |
When to use Scryfall instead
If you are building a Magic-only product, use Scryfall. It is free, the data is excellent, the search syntax is unmatched and there is no commercial reason to pay us instead. We use Scryfall as an upstream source and think you should too. Come back when you add a second game.
Migration
What the change looks like
Concepts map closely. Most migrations are a single afternoon of find-and-replace plus a test pass.
# Scryfall
curl "https://api.scryfall.com/cards/search?q=c:red+cmc<=2"# TCGGraph — same query, and the shape survives adding a second game
curl "https://api.tcggraph.com/v1/cards?game=magic-the-gathering&colors=R&manaValue=2" \
-H "Authorization: Bearer $TCGGRAPH_KEY"Signals
When it is worth switching
None of these are reasons on their own. Two or three together usually are.
- You are adding a second game and do not want to write a second ingestion layer, a second cache and a second price model.
- You need price history rather than a spot price — for a portfolio chart, a repricing job or a trend alert.
- You want to be told when a set publishes or a card's legality changes, instead of diffing bulk files on a cron.
- You need an uptime commitment and a support contact, because something you sell depends on the data being there.
Migration
Moving off Scryfall, step by step
The honest version, including the parts that are not one-to-one.
Step 1
Map the search syntax
Scryfall's query language is more expressive than any parameter-based API, and that is the part you will miss. Most real queries translate directly: c:ur becomes colors=U,R, cmc<=3 becomes maxManaValue=3, f:commander becomes format=commander. Anything genuinely exotic is usually easier to express as a GraphQL filter than as a query string.
Step 2
Switch the identifier you key on
Scryfall's oracle_id and id map to our oracleId and card id respectively, with the same meaning: one identifies the card as a rules object, the other identifies a single printing. If your database already stores oracle ids, your deck lists keep working unchanged.
Step 3
Move price reads off the card object
Scryfall attaches a small price object to each card. We return a price series per marketplace and finish, so you ask for what you need with include=prices rather than getting one blended number. This is more work on day one and considerably less work the first time somebody asks for a chart.
Step 4
Keep Scryfall where it is better
Plenty of teams run both: Scryfall for its search syntax on a Magic-only screen, us for everything cross-game. They are not mutually exclusive, and we would rather tell you that than pretend otherwise.
Field mapping
What each field becomes
The part that takes the longest is discovering that Scryfall spells the same concept differently. Here it is, written down.
| Scryfall | TCGGraph | Notes |
|---|---|---|
| oracle_id | magic.oracleId | Identical meaning. Stable across printings. |
| cmc | magic.manaValue | Renamed by Wizards in 2021; we follow the current term. |
| type_line | magic.typeLine | Same string, em dash included. |
| color_identity | magic.colorIdentity | Array of single-letter codes in both. |
| card_faces | magic.faces | Same nesting for double-faced and split cards. |
| legalities.commander | legalities.commander | Same keys, same four values. |
| prices.usd | prices[].market | Ours is an array by source and finish, not one field. |
| image_uris.normal | images.normal | Unmetered on both. No credit cost here either. |
FAQ
Common questions
Anything else, email hello@tcggraph.com. We will tell you if the answer is that you should stay where you are.
More comparisons