Skip to main content
Glama
Isendoum

Slay the Spire 2 MCP

by Isendoum
README.md
# Slay the Spire 2 MCP

Let an LLM play your local Slay the Spire 2 through standard MCP tools.
Tested with **Codex** and **Unsloth Studio**, including local models.

A C# game mod exposes structured state and actions on loopback HTTP. A Python
adapter provides seven tools over MCP STDIO. The MCP client supplies the model;
this project requires no model API key.

**Windows alpha:** the tested game version is **0.107.1**. Early Access updates
can break the bridge. See the [support matrix](docs/compatibility.md) for the
difference between tested features and unverified platforms or multiplayer.

## Quick start on Windows

You need:

- Your own Steam installation of Slay the Spire 2.
- [Git](https://git-scm.com/downloads/win),
  [uv](https://docs.astral.sh/uv/getting-started/installation/), and the
  [.NET 9 SDK](https://dotnet.microsoft.com/download/dotnet/9.0).
  The .NET runtime alone cannot build the mod.
- Python 3.11 or newer. uv can download a compatible Python automatically.
- An MCP client and a model that supports tool calling. Codex is optional.

Open PowerShell and run:

```powershell
git clone https://github.com/Isendoum/slay-the-spire-mcp.git
cd slay-the-spire-mcp
# Close the game before installing the mod.
.\scripts\setup.ps1 -InstallMod
```

The script finds Steam libraries, creates a locked Python environment in
`.venv`, builds the mod against your game, and installs it. Existing mod files
are backed up in `artifacts/backups/`; the installed port config is preserved.
The source release requires a local build and does not include game assemblies.

For Codex CLI registration during setup, use:

```powershell
.\scripts\setup.ps1 -InstallMod -RegisterCodex
```

If PowerShell blocks downloaded scripts, you can run setup with a policy that
applies only to that process:

```powershell
powershell.exe -NoProfile -ExecutionPolicy Bypass -File .\scripts\setup.ps1 -InstallMod
```

For a custom game location:

```powershell
.\scripts\setup.ps1 -GameDir 'D:\Steam Library\steamapps\common\Slay the Spire 2' -InstallMod
```

Alternatively, set `STS2_GAME_DIR`. Without `-InstallMod`, setup builds into
`artifacts/mod/` without installing. To set up only the Python adapter, use
`-SkipMod`; this needs neither the game nor .NET, but gameplay needs the mod.

Launch the game, accept its mod consent prompt, enable **STS2 MCP** in Mods,
and restart the game if prompted.

## Connect your MCP client

Generate configuration containing the actual absolute Python path:

```powershell
.\scripts\client-config.ps1
# For Codex TOML:
.\scripts\client-config.ps1 -Format codex
```

Use STDIO transport with that executable and the two arguments `-m` and
`sts2_mcp.server`. No working directory, environment variables, or OAuth are
required. Keep the checkout in its installed location; moving it requires
rerunning setup and updating the client's executable path.

For Unsloth Studio/Desktop, open **Chat -> MCP -> Add custom MCP**. Use
`slay-the-spire-2` as the name, the generated Python path as **URL or executable**,
and add `-m` and `sts2_mcp.server` as separate argument rows. Test the connection,
add the server, and enable both its toggle and **Use MCP Servers**.

The [client guide](docs/clients.md) includes Codex registration, generic JSON,
and Unsloth troubleshooting.

## Verify and play

With the game open and the mod enabled:

```powershell
.\.venv\Scripts\python.exe -m sts2_mcp.server --doctor
.\.venv\Scripts\python.exe scripts\smoke-test.py --live
```

These checks read game state without making gameplay decisions. To check only
MCP startup and tool discovery without contacting the game, omit `--live`.

Ask your model:

> Use the slay-the-spire-2 MCP to continue my current run. Start with
> health_check, get_game_state, and get_action_help. Make one decision at a time
> using current state, and wait through transitions. Do not abandon my run or
> change profiles.

To start a new run, explicitly ask for the character and difficulty you want.

| Tool | Purpose |
| --- | --- |
| `health_check` | Check the game connection |
| `get_game_state` | Read the current screen, cards, enemies, intents, and choices |
| `get_action_help` | Get argument syntax for the 29 gameplay actions |
| `take_action` | Play cards, navigate, choose rewards/events, and buy items |
| `wait_for_player` | Wait through enemy turns and loading |
| `search_wiki` | Look up discovered card and relic rules |
| `get_profile` | Read active profile progress |

Indices start at zero and can shift after every action. Use target IDs from the
current state. Actions are never automatically retried. A timeout can mean the
action executed; read state before deciding whether to try again. The returned
`after` state can still show a transition; use `wait_for_player` or read again.
Supply `expected_state_id` to reject an already stale decision; it is a
best-effort check, not a transaction with the game's animation queue.

## Connection and troubleshooting

The mod's `http://127.0.0.1:15526` address is a **REST game bridge**, not an MCP
HTTP endpoint. Connect your MCP client to the Python executable over STDIO.

- **Missing prerequisite:** follow the installer error, then reopen PowerShell.
- **Game not found:** pass `-GameDir` or set `STS2_GAME_DIR`.
- **Missing game DLL or compile errors after an update:** verify the game files
  in Steam and check the [supported version](docs/compatibility.md). Rebuild
  using `.\scripts\build-mod.ps1`; source changes may be needed after game updates.
- **Connection refused:** keep the game open, confirm mod consent and activation,
  and check the game's Godot log for `[STS2 MCP]` messages.
- **Port conflict:** edit the `port` in `STS2_MCP.conf` beside the installed mod,
  restart the game, and pass the matching `--bridge-url http://127.0.0.1:PORT`
  to the Python server or set `STS2_BRIDGE_URL`.
- **No tools:** restart or refresh the client after registration and enable its
  MCP server toggle. For Unsloth remote/LAN settings, see [the client guide](docs/clients.md).

Only loopback bridge origins are accepted. Environment proxies are ignored,
and the mod rejects browser-origin requests. Other processes on the computer
can access the bridge; it has no authentication. See [SECURITY.md](SECURITY.md).

## Updates and removal

Close the game, pull the latest source, and rerun the same setup command.
Backups are made before existing mod files are replaced.

To uninstall, close the game and remove `STS2_MCP.dll`, `STS2_MCP.json`, and
optionally `STS2_MCP.conf` from its `mods` folder. For Codex, run
`codex mcp remove slay-the-spire-2`; remove the server entry from other clients.
You may then delete the checkout. To restore an older mod, copy its two files
from the matching directory in `artifacts/backups/` with the game closed.

## Development and licensing

See [CONTRIBUTING.md](CONTRIBUTING.md) for tests and local development,
[CHANGELOG.md](CHANGELOG.md) for release history, and
[docs/bridge-api.md](docs/bridge-api.md) for the game protocol.

MIT licensed. The bridge is adapted from
[Gennadiyev/STS2MCP](https://github.com/Gennadiyev/STS2MCP); its original copyright
and license are retained. See [THIRD_PARTY_NOTICES.md](THIRD_PARTY_NOTICES.md).
This community project is not affiliated with or endorsed by Mega Crit.
The license covers this integration, not Slay the Spire 2 or its assets.

TDQS

A3.7/5.0

Scored across 7 tools

Disambiguation4/5

Most tools are clearly distinct: state reading (get_game_state), action discovery (get_action_help), acting (take_action), waiting (wait_for_player), and reference lookups (search_wiki, get_profile) target different needs. The descriptions explicitly clarify the tricky boundary between get_action_help (syntax) and get_game_state (actual choices), though health_check and get_game_state overlap slightly since both report game status.

Naming Consistency5/5

All tools use consistent snake_case with clear verb_noun or verb_object patterns (get_game_state, take_action, search_wiki, wait_for_player). The get_* family is predictable and no casing or verb-style mixing appears.

Tool Count5/5

Seven tools is well-scoped for an agent-driven game controller, covering status, read, help, act, wait, and profile/reference lookups without redundancy. Each tool earns its place in the gameplay loop.

Completeness4/5

The core agent loop (health, state, help, action, wait) plus profile/wiki lookups is well covered. Minor gaps exist around save/load, restart, or deck-management operations, but these are workable given the bridge exposes actions through take_action.

Maintenance

ActivityMaintained
ResponsivenessNo issues