
Research
/Security News
Popular npm Packages in the keyv and Cacheable Namespaces Compromised in Active Supply Chain Attack
Popular npm packages keyv and cacheable compromised.
lorcana-mcp
Advanced tools
MCP server that connects Claude to Disney Lorcana card data. Export your collection from TCGPlayer, hand it to Claude, and get it fully enriched with ink cost, stats, keywords, abilities, and format legality — plus a ready-to-import file for dreamborn.ink.
What it does: plug this into Claude and it becomes a Disney Lorcana expert that knows your actual collection — no more tab-switching between TCGPlayer, dreamborn.ink, and a wiki.
Once it's connected, you can just talk to Claude like:
Everything reads from public card APIs plus your own exported CSV — no account, no login, nothing to configure.
1. Install it:
pip install lorcana-mcp
2. Connect it to Claude:
claude mcp add lorcana -- lorcana-mcp serve
(Using Claude Desktop instead? See Add to Claude below.)
3. Talk to it: Export your collection from TCGPlayer (My Account → My Collection → Export), then just say:
"Enrich my collection at /path/to/your/export.csv"
That's it — Claude does the rest. Everything below is reference detail for when you want more control.
Ten tools are available in Claude once the server is running:
| Tool | What it does |
|---|---|
enrich_csv | Enriches a raw TCGPlayer export with Ink, Cost, Type, Subtypes, STR/WIL/Lore, Inkable, Keywords, and Abilities. Writes an enriched CSV and a dreamborn.ink-ready import file next to the input. refresh_prices=True also refreshes TCG Market Price with a live tcgcsv.com lookup. |
lookup_card | Looks up any card by name. Returns full stats, ability text, format legality, and card image URL. |
resolve_card | Fuzzy-resolves an informal, misspelled, or subtitle-less card name (e.g. "goofy musketeer", "elsa"). Returns a single confident match, a ranked top-3 to disambiguate, or nothing found. |
search_cards | Searches the full card pool by color, type, rarity, set, cost range, keyword, ability text, or subtype — with pagination. |
find_song_synergies | Finds every character that can sing a given song (or a raw cost threshold), split into Singer-keyword discount picks and plain cost-qualifiers. Optionally flags which ones you own. |
filter_collection | Filters your collection to cards legal in a given format: core, infinity, core_zh, core_ja, or poorcana. |
audit_csv | Compares an enriched collection against live API data and reports any stale or wrong fields. |
analyze_deck | Analyzes a raw deck list (4x Card Name per line) for ink curve, inkable split, color split, card types, estimated lore/turn, and Core Constructed legality (60-card min, max 4 copies, ≤2 ink colors). |
what_am_i_missing | Compares a deck list against your collection: what you already own, what's missing or short, and a live TCGPlayer cost estimate (via tcgcsv.com) to complete it. |
build_deck | Automatically assembles a legal, curve-balanced ~60-card decklist for an ink pair/format, in one of 3 modes: collection (only cards you own), ideal (best deck regardless of ownership, priced to complete if you pass a collection CSV), or market (best deck, fully priced, ignoring ownership). A heuristic curve/keyword-value builder, not a synergy/combo detector. |
| Directory | Link |
|---|---|
| MCP Registry (official) | registry.modelcontextprotocol.io |
| mcp.so | mcp.so/server/lorcana-mcp |
| PyPI | pypi.org/project/lorcana-mcp |
pip install lorcana-mcp
Or from source:
git clone https://github.com/IcaroBichir/lorcana-mcp
cd lorcana-mcp
pip install .
claude mcp add lorcana -- lorcana-mcp serve
Find claude_desktop_config.json (macOS: ~/Library/Application Support/Claude/, Windows: %APPDATA%\Claude\) and add:
{
"mcpServers": {
"lorcana": {
"command": "lorcana-mcp",
"args": ["serve"]
}
}
}
Restart Claude Desktop after saving.
Any client that supports stdio MCP servers can use lorcana-mcp serve as the command.
Once the server is connected, just talk to Claude naturally. No slash commands needed.
Export your collection from TCGPlayer → My Collection → Export CSV, then:
"Enrich my collection at /Users/me/Downloads/Lorcana_063026.csv"
Claude will fetch card data from the APIs and write two files next to your input:
enriched_Lorcana_063026.csv — your collection with 10 new columnsdreamborn_Lorcana_063026.csv — ready to import at dreamborn.inkOn re-runs, pass the previous enriched file as a cache to skip already-seen cards:
"Enrich /Users/me/Downloads/Lorcana_new.csv using /Users/me/lorcana/enriched_Lorcana_old.csv as cache"
To refresh prices on demand without re-exporting from TCGPlayer:
"Re-enrich my collection at /Users/me/lorcana/enriched_Lorcana_063026.csv and refresh prices"
refresh_prices=True overwrites each row's TCG Market Price with a live tcgcsv.com lookup for that exact printing — useful when an enriched CSV's prices are stale.
"Look up Mirage - Super Recruiter"
"What are the stats on Alma Madrigal - Heart of the Family?"
"Is Will o' the Wisp legal in Core?"
Returns: ink color, cost, type, subtypes, STR/WIL/Lore, inkable status, keywords, full ability text, format legality, and a card image URL.
"Find the card 'goofy musketeer'"
"What's that card 'big pete'?"
"Look up 'elsa' — not sure which version"
Tokenizes the query and scores it against every card's name and subtitle, tolerating missing dashes, missing subtitles, word order, and minor typos. Returns full detail for a single confident match, a ranked top-3 with confidence scores when several cards are plausible (e.g. a bare name matching every printing of that character), or nothing if the query doesn't resemble any card.
"Show me all Evasive characters in Amethyst that cost 3 or less"
"Find Toy characters"
"Search for Rare Steel cards from Wilds Unknown"
Filters: ink color(s), card type (Character / Action / Item / Location / Song), rarity, set name, cost range, keyword, ability text substring, and subtype — all combinable, plus pagination (offset + limit). Results are grouped by ink color and sorted by cost.
"Which characters can sing Be Our Guest?"
"Show me Amber characters that can sing a cost-7 song"
"Who can sing Friends on the Other Side, and which ones do I own?" (pass your enriched collection CSV)
A character can sing a song if its printed cost meets the song's cost outright, or it has a matching Singer X keyword — Singer lets a cheap character punch above its actual cost for singing purposes only. Results split into Singer-keyword "discount" picks (highest Singer value, then cheapest actual cost) and plain cost-qualifiers (cheapest first). Pass collection_csv to flag ownership.
"Which of my cards are legal in Core Constructed?"
"Show me my Infinity-legal cards grouped by ink color"
"What Poorcana-legal cards do I have in Amber?"
Valid formats: core, infinity, core_zh, core_ja, poorcana
Poorcana filtering uses the Rarity column in your enriched CSV (Common + Uncommon only) — no API call needed.
Core/Infinity/regional legality comes from duels.ink, which tracks the current rotation for each region.
"Audit my collection at /Users/me/lorcana/enriched_collection.csv"
Useful after a new set releases or if a card's data looks wrong. Compares every non-promo card against live API data and reports field-by-field discrepancies.
"Analyze this deck: 4x Goofy - Musketeer, 4x Elsa - Spirit of Winter, ..." (paste a full list, one card per line)
Accepts 4x Card Name or 4 Card Name; quantity defaults to 1 if omitted. Lines starting with # or // are treated as comments.
Returns: ink curve (1-2/3-4/5-6/7+ cost brackets), inkable vs. uninkable count, color split, card type split, an estimated lore-per-turn (sum of Character lore values), a Core Constructed legality check (60-card minimum, max 4 copies of any card, at most 2 ink colors), and any card names that couldn't be resolved.
"What am I missing to build this deck?" (paste the deck list and point me at your collection CSV)
"How much would it cost to finish this Amber/Steel list?"
Same deck list format as analyze_deck. Cross-references against your enriched collection CSV, then splits results into cards you already have enough of and cards you're missing or short on. For cards you're short on (own at least one printing already), the cost comes straight from the CSV's own TCG Market Price column — no network call needed. Only cards you own zero copies of fall back to a live TCGPlayer lookup via tcgcsv.com (cheapest printing across all sets/rarities, since gameplay is identical), and even then only if at least one card actually needs it. Live price data is cached for 24h, so the first call that needs it takes a bit longer while it warms up.
The enricher adds these 10 columns to the raw TCGPlayer export:
| Column | Description |
|---|---|
| Ink | Ink color(s) — dual-ink cards show both, e.g. Amber, Steel |
| Ink Cost | Numeric cost to play (1–12) |
| Card Type | Character / Action / Action - Song / Item / Location |
| Subtypes | e.g. Storyborn, Hero, Toy |
| Strength | ⚔ stat — blank for Actions, Items |
| Willpower | 🛡 stat — blank for Actions, Items |
| Lore Points | ◆ gained per quest — blank for Actions, Items |
| Inkable | Yes / No |
| Keywords | Comma-separated: Evasive, Shift 3, Singer 5, Resist +1, etc. |
| Abilities | Full card text, pipe-separated lines |
| Source | Sets | Used for |
|---|---|---|
| LorcanaJSON | All sets (1–14+) | Primary source for Set 12+; fallback for 1–11 |
| lorcana-api.com | Sets 1–11 | Preferred for Sets 1–11 (richer body text) |
| duels.ink | All sets | Format legality, card images |
Card data is cached locally for 24 hours at ~/.cache/lorcana-mcp/. Manage the cache with the CLI:
lorcana-mcp cache stats # show entry count, expiry status, and file size
lorcana-mcp cache clear # delete all cached responses (fresh fetch on next use)
| Set | Name |
|---|---|
| 1 | The First Chapter |
| 2 | Rise of the Floodborn |
| 3 | Into the Inklands |
| 4 | Ursula's Return |
| 5 | Shimmering Skies |
| 6 | Azurite Sea |
| 7 | Archazia's Island |
| 8 | Reign of Jafar |
| 9 | Fabled |
| 10 | Whispers in the Well |
| 11 | Winterspell |
| 12 | Wilds Unknown |
| 13 | Attack of the Vine! |
| 14 | Hyperia City |
New sets are picked up automatically via LorcanaJSON as long as the set name is added to the internal mapping. Open an issue if a new set isn't resolving.
Go to TCGPlayer → My Account → My Collection → Export. The raw file has columns like Product Name, Set Name, Number, Rarity, Condition, Printing, and Add to Quantity (this is the real owned-quantity column — Total Quantity is always blank in exports).
Promo cards: resolved automatically where possible. dreamborn.ink's bulk import represents a promo as
(Set Number, Card Number)whereSet Numberis the LJ set the promo drop is tied to andCard Numberis the full"N/Series"string (e.g."57/P3") — verified against a real dreamborn export, not just its card-browser display (an earlier attempt based on the display alone silently corrupted imports; see CHANGELOG.md's 0.2.2/0.2.3 entries). Any promo not yet in that map still needs manual entry via dreamborn.ink's card search after importing the rest.
lorcana-mcp --version
lorcana-mcp serve Start the MCP server (stdio)
lorcana-mcp cache stats Show cache info
lorcana-mcp cache clear Clear cached API responses
git clone https://github.com/IcaroBichir/lorcana-mcp
cd lorcana-mcp
python -m venv .venv && source .venv/bin/activate
pip install -e ".[dev]"
pytest
205 tests, no network calls required.
MIT — see LICENSE.
If you're an AI agent (Claude or otherwise) with this MCP server connected, read this section before making tool calls. It's the fast path to using this correctly.
| The user wants... | Call... | Not... |
|---|---|---|
| Their raw TCGPlayer export turned into a real database | enrich_csv | — |
| To bring stale prices up to date without re-exporting | enrich_csv with refresh_prices=True | manually curling TCGPlayer |
| Stats on a card whose exact name they gave you | lookup_card | — |
| A card by an informal, partial, or misspelled name (e.g. "goofy musketeer", "big pete", "elsa") | resolve_card | lookup_card — it only does plain substring matching and will falsely report "not found" for anything without exact dashes/spelling |
| To browse/filter the whole card pool (by color, type, rarity, set, cost, keyword, ability text, subtype) | search_cards | — |
| Singer combos / "who can sing this song for free" | find_song_synergies | — |
| Format legality of their collection (Core, Infinity, Poorcana, etc.) | filter_collection | — |
| To sanity-check an enriched CSV against live data | audit_csv | — |
| A decklist rated for curve, color balance, and legality | analyze_deck | — |
| "What do I need to buy to finish this deck, and how much?" | what_am_i_missing | — |
| "Build me a deck for [ink pair]" | build_deck — ask which of the 3 modes (collection/ideal/market) first if the user hasn't said | manually assembling a decklist from search_cards results |
csv_path / input_path / collection_csv. Relative paths resolve against the server process's cwd, not the user's — this fails silently or points at the wrong file. If you don't have an absolute path, ask the user or find the file first.resolve_card over lookup_card unless the user gave you a name you're confident is exact and correctly spelled. When in doubt, resolve_card is strictly more forgiving and costs nothing extra.find_song_synergies, what_am_i_missing, and build_deck already call tcgcsv.com internally with 24h caching and cheapest-printing logic. Don't curl TCGPlayer or scrape prices yourself.lorcana-mcp cache clear before assuming a tool is broken — card and price data is cached 24h.resolve_card and find_song_synergies can return a ranked "did you mean" list instead of a single answer — present it to the user rather than guessing which one they meant.build_deck is a curve/keyword-value heuristic, not a synergy engine. It doesn't detect multi-card combos (Merlin/Mim bounce, Steelsong, etc.) — don't present its output as a finished, tournament-tuned decklist. Treat it as a strong starting point to review and adjust, not a final answer.Product ID (CSV column 1) ≠ TCGplayer Id (column 2). Only Product ID matches external pricing APIs (LorcanaJSON's externalLinks.tcgPlayerId, tcgcsv.com's productId). Column 2 is an unrelated secondary ID — if you're ever writing custom code against this data, matching on it silently returns zero results.PROMO_DREAMBORN_ROW/PROMO_DREAMBORN_ROW_BY_NUMBER (api.py) — verified against a real dreamborn.ink export, not its card-browser display (an earlier browser-based guess silently corrupted a real import; CHANGELOG.md 0.2.2). A promo's dreamborn Card Number is the full "N/Series" string, not split into a separate series field — don't re-split it if extending this map. Anything not yet in the map still needs manual entry via dreamborn.ink's search after importing.search_cards and find_song_synergies already deduplicate alt-art/Enchanted reprints by name internally, so don't be surprised the count is lower than you'd expect from a raw card list.pytest before and after any change — 205 tests, all network-free (external calls are mocked).api.py (card data + fuzzy matching + pricing), deck.py (deck list parsing/analysis), and enricher.py (CSV pipeline). server.py only wraps those as MCP tools and formats output — keep it that way rather than putting logic directly in tool functions.pyproject.toml (version), server.json (version, for the MCP Registry), CHANGELOG.md (entry), and this README if tool behavior changed. Check git log for the pattern.python -m build, twine upload, mcp-publisher publish) — never assume a version bump in pyproject.toml means it's live on PyPI or the registry. Check before telling a user a feature is "available."FAQs
MCP server for enriching Disney Lorcana TCG card collections from TCGPlayer exports
We found that lorcana-mcp demonstrated a healthy version release cadence and project activity because the last version was released less than a year ago. It has 1 open source maintainer collaborating on the project.
Did you know?

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Research
/Security News
Popular npm packages keyv and cacheable compromised.

Security News
A misconfiguration gave three Anthropic models internet access, and one, believing it was in a simulation, shipped a credential-stealing package to PyPI.

Security News
/Company News
Socket has joined the new Composer and Packagist sponsorship program as a launch sponsor, supporting the team that keeps PHP's package ecosystem secure.