{
  "markdown": "<!-- mcp-name: io.github.parkseokjune/kaggle-mcp -->\n\n# kaggle-mcp\n\n[![CI](https://github.com/parkseokjune/kaggle-mcp/actions/workflows/ci.yml/badge.svg)](https://github.com/parkseokjune/kaggle-mcp/actions/workflows/ci.yml)\n[![PyPI](https://img.shields.io/pypi/v/safe-kaggle-mcp)](https://pypi.org/project/safe-kaggle-mcp/)\n[![smithery](https://smithery.ai/badge/parkseokjune/kaggle-mcp)](https://smithery.ai/server/parkseokjune/kaggle-mcp)\n[![Python](https://img.shields.io/pypi/pyversions/safe-kaggle-mcp)](https://pypi.org/project/safe-kaggle-mcp/)\n[![License: MIT](https://img.shields.io/badge/License-MIT-green.svg)](LICENSE)\n\nA **safety-first** [Model Context Protocol](https://modelcontextprotocol.io) server connecting Claude (Desktop / Code) to [Kaggle](https://www.kaggle.com) — competitions, datasets, kernels (notebooks), and models.\n\n> **safe-kaggle-mcp is the only Kaggle MCP built safety-first.** Every irreversible action — submit, delete, public-publish — is gated behind a two-call preview→commit confirm token, a per-competition submission budget surfaced in every response, and off-by-default destructive flags, while all Kaggle-returned text is fenced in `<untrusted-content>` and your credentials never enter the model context. Other servers chase tool count and the official remote server wins on zero-install convenience — but **none of them, official included, gate a single destructive call, cap submissions, or harden against prompt injection.** It trades raw breadth for the one thing an autonomous agent with your Kaggle account actually needs: it *cannot* quietly burn your daily submissions, leak your key, publish your private work, or be hijacked by a poisoned discussion thread.\n\n```bash\nclaude mcp add --transport stdio kaggle -- uvx --from safe-kaggle-mcp kaggle-mcp\n```\n\n## How it compares\n\n| Feature | **safe-kaggle-mcp** | Typical community server | Official remote / Composio |\n|---|---|---|---|\n| Two-call preview→commit confirm tokens (submit/delete/publish) | ✅ **Yes** | ❌ No (single-shot) | ❌ No (single-shot) |\n| Per-competition submission budget surfaced to the agent | ✅ **Yes** (default 5/day) | ❌ No | ❌ No (opaque server quota) |\n| Prompt-injection hardening (`<untrusted-content>` fencing) | ✅ **Yes** | ❌ No | ❌ No |\n| Private-by-default + off-by-default destructive/publish flags | ✅ **Yes** | ⚠️ Optional `is_private` param | ❌ No |\n| No in-chat `authenticate()` + 40-hex credential redaction | ✅ **Yes** | ❌ Some leak the key into context | ⚠️ OAuth keeps key out, no redaction |\n| Zip-slip-safe / sandboxed downloads | ✅ **Yes** | ❌ No | ❌ Can't sandbox local writes |\n| Callable local **EDA** tool (compact pandas digest, never raw rows) | ✅ **Yes** (dataset + competition) | ❌ EDA *prompt* at best | ❌ No |\n| Competition **train/test schema diff** + target auto-detect | ✅ **Yes** | ❌ No | ❌ No |\n| Competition **landscape** triage (days-left, budget, metric) | ✅ **Yes** | ❌ Thin raw list | ❌ Raw fields, no digest |\n| **Submission best-score** digest (metric-aware best/trend/failures) | ✅ **Yes** | ❌ Raw list | ❌ Raw list |\n| **Leaderboard delta tracking** (local snapshots + rank moves) | ✅ **Yes** | ❌ No | ❌ No API endpoint either |\n| Session **audit ledger** of mutating actions (redacted) | ✅ **Yes** | ❌ No | ❌ No |\n| Read-only **discussion + write-up digest**, injection-fenced | ✅ **Yes** (untrusted-fenced) | ⚠️ Yes but **unfenced** (Galaxy-Dawn) | ⚠️ Unfenced |\n| **One-call competition kickoff** (data + EDA + baseline plan) | ✅ **Yes** | ❌ No | ❌ No |\n| Output discipline (ranked/capped tables, pagination, top-N) | ✅ **Yes** | ❌ Undocumented | ❌ Client's job |\n| Modern `KGAT_` token + legacy username/key auth | ✅ **Both** | ⚠️ Mostly legacy-only | ✅ OAuth 2.0 |\n| Install | Local stdio (PyPI + git, `uvx`) | Local (pip/uv) | ✅ Zero-install remote |\n| Raw tool breadth | 41 tools (no benchmark listing — API exposes none) | up to ~51 | ~35–57 |\n\nThe two honest places we don't lead: the **official** remote server is zero-install, and the broadest **community** server (Galaxy-Dawn, ~51 tools) has more raw endpoints (e.g. benchmarks). Where they expose ~10 forum tools *unfenced*, we expose read-only discussion **search + read** with every body fenced as `<untrusted-content>` — and no posting tool, because [the API has none](#what-it-wont-do-honest-limits).\n\n## What you can do with it\n\nDrive your whole Kaggle workflow from a Claude chat, in plain language:\n\n| Ask Claude… | What happens under the hood |\n|---|---|\n| *\"Triage active competitions — prize, metric, days left.\"* | `kaggle_competition_landscape` (one digested, deadline-sorted report) |\n| *\"Download titanic data, infer the target, and do an EDA.\"* | `kaggle_eda_competition` → train/test schema diff (auto-target) + compact pandas digest |\n| *\"Find a good Titanic dataset and show me what it looks like.\"* | `kaggle_search_datasets` → `kaggle_dataset_preview` (capped, untrusted-fenced rows) |\n| *\"Summarize the iris dataset.\"* | `kaggle_eda_dataset` → shape, dtypes, missingness, target dist, top correlations |\n| *\"Submit predictions.csv to titanic and tell me the score.\"* | `kaggle_preview_submission` → `kaggle_submit_to_competition` (token + budget gate) → `kaggle_get_submission_score` |\n| *\"Is it worth iterating — what's my best score so far?\"* | `kaggle_submission_best_score` (metric-aware best/trend/failures + today's budget) |\n| *\"Did anyone pass me on the leaderboard since last check?\"* | `kaggle_leaderboard_track` (snapshot deltas, who passed you) |\n| *\"What techniques are people discussing for this competition?\"* | `kaggle_search_discussions` → `kaggle_get_discussion` (read-only, every post untrusted-fenced) |\n| *\"Find the winning solution write-ups for this competition.\"* | `kaggle_search_writeups` → `kaggle_get_discussion` |\n| *\"Kick off this competition for me.\"* | `kaggle_competition_kickoff` — one call: metric + rules + data download + train/test EDA (auto-target) + baseline plan + budget |\n| *\"What mutating actions have I taken this session?\"* | `kaggle_audit_log` (redacted ledger of every submit/create/delete) |\n| *\"Run this notebook on Kaggle's free GPU and get the output.\"* | `kaggle_push_kernel` → `kaggle_kernel_status` → `kaggle_kernel_output` |\n| *\"Save my engineered features as a private dataset version.\"* | `kaggle_version_dataset` — **private by default** |\n\n**Higher-order workflows the agent chains itself:** an autonomous competition loop (download → train → submit → read score → iterate, within the daily budget), Kaggle as a remote GPU/TPU backend, and cross-run memory via private dataset versions. Every irreversible step is gated, so the agent can run autonomously without risking your account.\n\n## What it won't do (honest limits)\n\nSome competitors advertise capabilities the public Kaggle API can't actually deliver. We refuse to ship dishonest stubs:\n\n- **No posting to forums/discussions.** The API can *read* topics but has no create/reply/vote endpoint — so we don't pretend to.\n- **No private-leaderboard or final-rank prediction.** Private scores are withheld until the deadline; our tools label scores as **public-only**.\n- **No historical leaderboard from Kaggle.** There's no such endpoint — `kaggle_leaderboard_track` diffs against snapshots *you* captured locally, and says so.\n- **No hidden test labels / private splits.** We only ever serve files the competition exposes.\n\n## Install\n\n```bash\n# fastest: install + register with Claude Code\nclaude mcp add --transport stdio kaggle -- uvx --from safe-kaggle-mcp kaggle-mcp\n\n# or straight from this repo (no PyPI):\nclaude mcp add --transport stdio kaggle -- uvx --from git+https://github.com/parkseokjune/kaggle-mcp kaggle-mcp\n\n# or for development\nuv sync --extra dev && uv run kaggle-mcp\n```\n\n> The PyPI distribution is **`safe-kaggle-mcp`** (the name `kaggle-mcp` was taken); the command it installs is still `kaggle-mcp`, so launch it with `uvx --from safe-kaggle-mcp kaggle-mcp`.\n\nGet a token at <https://www.kaggle.com/settings> → **API** → **Create New Token**. Both schemes work (resolved in order):\n\n```bash\n# 1) legacy username/key (env or ~/.kaggle/kaggle.json)\nexport KAGGLE_USERNAME=your_user\nexport KAGGLE_KEY=your_40_char_key\n\n# 2) current API token (KGAT_...): the client reads it automatically\nmkdir -p ~/.kaggle && echo \"KGAT_...\" > ~/.kaggle/access_token && chmod 600 ~/.kaggle/access_token\n```\n\n**Claude Desktop** — edit `claude_desktop_config.json`, then fully restart:\n```json\n{ \"mcpServers\": { \"kaggle\": {\n  \"command\": \"uvx\", \"args\": [\"--from\", \"safe-kaggle-mcp\", \"kaggle-mcp\"],\n  \"env\": { \"KAGGLE_USERNAME\": \"your_user\", \"KAGGLE_KEY\": \"your_key\" } } } }\n```\n\n## Safety switches (default OFF → read-only / private posture)\n\n| Env var | Default | Effect when `1` |\n|---|---|---|\n| `KAGGLE_MCP_ENABLE_DESTRUCTIVE` | `0` | Exposes `kaggle_delete_dataset` / `kaggle_delete_model` |\n| `KAGGLE_MCP_ENABLE_PUBLISH` | `0` | Allows creating **public** datasets |\n| `KAGGLE_MCP_SUBMISSION_CAP` | `5` | Per-competition daily submission budget |\n\nEven when enabled, each destructive call still needs a one-time `confirm_token` from its `*_preview_*` tool, and is recorded in `kaggle_audit_log`.\n\n## Tools\n\n**41 tools** across account, competitions, datasets, discussions, kernels, models — plus `kaggle://` resources (metadata, leaderboard, rules) and `/kaggle-eda`, `/kaggle-submit-checklist`, `/kaggle-landscape`, `/kaggle-solution-research` prompts. Run `kaggle_status` to see your auth + submission budget.\n\nVerified live against the Kaggle API (`kaggle` 2.2.2) with both auth schemes; 53 offline + 6 live read-only tests pass.\n\n## Develop\n\n```bash\nuv run pytest                              # offline unit + integration tests\nKAGGLE_LIVE=1 uv run pytest tests/test_live_readonly.py   # live read-only smoke (needs creds)\nuv run mcp dev src/kaggle_mcp/server.py    # MCP Inspector\n```\n\n## License\n\nMIT\n",
  "bytes": 9884,
  "sha": "6f86420a572bb3392c41672c5a735f5bc5ca72b8f7c4c3a378e4d2b52d91ab3c",
  "repo_slug": "parkseokjune/kaggle-mcp",
  "fonte": "repo",
  "truncated": false,
  "api": "https://agentalog.com/api/listings/mcp_io_github_parkseokjune_kaggle_mcp_52dbda09/readme"
}