Skip to content

phase-rs/phase

phase.rs

An open-source Magic: The Gathering rules engine and game client

Play Preview Play Online Download Support on Ko-fi

Quick Start · Features · Architecture · Development · Discord · Ask DeepWiki

Card Coverage Keywords Cards
Pauper Pioneer Modern Standard Legacy Vintage Commander


phase.rs gameplay

A Rust-native MTG engine compiling to native and WASM, powering a Tauri desktop app, browser PWA, and WebSocket multiplayer. Implements comprehensive MTG rules using functional architecture — pure reducers, discriminated unions, and immutable state with structural sharing — with an Arena-quality React/TypeScript UI.

Story

I'm Matt — a millennial software engineer who loves Magic. My six-year-old son asks me to play with him all the time, but the real game is just too complicated for a kid his age.

So I built Alchemy (source) — a simplified, kid-friendly version of MTG we could play together on our iPads. Fewer keywords, no lands, energy that builds each turn, and an adaptive learning mode where he solves math problems for combat bonuses. I had a working version in a single afternoon and fleshed it out over the following week.

After that I wanted to see how far I could push it — a real MTG rules engine in Rust, compiling to WASM, with the same React frontend so the whole thing runs in a browser. This whole project went from nothing to where it is now in a matter of weeks.

I'm not trying to make money off this. There are no ads. I'm just a dude who likes Magic.

Features

  • Rules engine — Turns, priority, stack, combat, state-based actions, layers, triggers, replacement effects
  • 34,300+ cards — Parsed from MTGJSON with format support (Commander, Modern, Pioneer, Standard, and more)
  • AI opponent — Per-card decision logic, game tree search, and evaluation heuristics
  • Game UI — Battlefield, hand, stack, targeting overlays, mana payment, animations, and ambient audio
  • Multiplayer — WebSocket server with hidden information, lobby system, and WebRTC peer-to-peer
  • Metagame feeds — Automated scraping of top decks from MTGGoldfish, updated daily
  • Deck builder — Card search, visual builder, and .dck/.dec import
  • Cross-platform — Tauri desktop (Windows, macOS, Linux), browser PWA, and tablet
  • Card images — Scryfall integration with IndexedDB caching

Contribute a Card with Your LLM

Thousands of cards are still unimplemented. If you use Claude Code, Codex CLI, or a similar agent, you can "lend your LLM" an hour and ship a real PR — even if you don't have a Rust toolchain. The LLM does all the work; you just paste a prompt.

Hand this to your LLM:

Read https://raw.githubusercontent.com/phase-rs/phase/main/docs/AI-CONTRIBUTOR.md
and follow it end-to-end to implement {a card I name, or pick one for me}.
Use medium thinking. Don't stop for my input. Open a PR when done.

Full procedure, two tracks (developer / non-developer), and copy-paste prompts for LLM UIs without web fetch: docs/AI-CONTRIBUTOR.md.

Quick Start

Prerequisites

  • Rust toolchain
  • wasm32 target: rustup target add wasm32-unknown-unknown (Windows: see below)
  • wasm-bindgen-cli: cargo install wasm-bindgen-cli@0.2.114
  • wasm-opt (optional): brew install binaryen or apt install binaryen
  • Node.js 22+ and pnpm: npm i -g pnpm

Windows

rustup on Windows defaults to the GNU toolchain, which requires dlltool.exe and fails with "error calling dlltool 'dlltool.exe': program not found". You need Visual Studio Build Tools with the Desktop development with C++ workload, then switch to the MSVC host:

rustup set default-host x86_64-pc-windows-msvc
rustup toolchain install nightly --target wasm32-unknown-unknown

Verify with rustup show active-toolchain — it should end in x86_64-pc-windows-msvc.

The setup scripts also require jq and curl, which are not installed by default on Windows. Install them before running ./scripts/setup.sh:

winget install jqlang.jq
winget install curl.curl   # skip if curl is already on your PATH

Open a new terminal after installing so the updated PATH takes effect.

Setup

git clone https://github.com/phase-rs/phase && cd phase
./scripts/setup.sh     # Downloads card data, builds WASM, installs deps
cd client && pnpm dev  # Start dev server at localhost:5173

Manual Steps

./scripts/gen-card-data.sh            # generate card-data.json
./scripts/build-wasm.sh               # Build WASM bindings
cd client && pnpm install && pnpm dev # Start frontend

Architecture

Rust Workspace (crates/)

Crate Description
engine Core rules engine: types, game logic, parser, card database
phase-ai AI opponent: evaluation, legal actions, search
engine-wasm WASM bindings via wasm-bindgen + tsify
server-core Server-side game session management
phase-server Axum WebSocket server for multiplayer
feed-scraper Metagame deck scraper (MTGGoldfish)

Dependency flow: engine <- phase-ai <- engine-wasm / server-core <- phase-server (feed-scraper is standalone)

Frontend (client/)

React + TypeScript + Tailwind v4 + Zustand + Framer Motion + Vite

Transport-agnostic EngineAdapter interface with multiple implementations:

  • WasmAdapter — Direct WASM calls (browser/PWA)
  • TauriAdapter — Tauri IPC (desktop)
  • WebSocketAdapter — WebSocket (multiplayer)
  • P2PHostAdapter / P2PGuestAdapter — WebRTC peer-to-peer via PeerJS

Design Principles

  • Pure reducersapply(state, action) -> ActionResult with no mutation
  • Discriminated unions — Rust enums serialize to tagged TS unions via serde + tsify
  • Structural sharing — Immutable state via rpds persistent data structures

Development

Build Commands

# Rust (uses cargo-nextest for test execution)
cargo test-all                             # Run all tests (nextest)
cargo clippy --all-targets -- -D warnings  # Lint
cargo fmt --all -- --check                 # Format check

# WASM
./scripts/build-wasm.sh                    # Build WASM (release)
./scripts/build-wasm.sh debug              # Build WASM (debug)

# Frontend
cd client
pnpm install                               # Install dependencies
pnpm dev                                   # Vite dev server
pnpm build                                 # TypeScript check + Vite build
pnpm lint                                  # ESLint
pnpm test                                  # Vitest

Cargo Aliases

cargo test-all          # Run all tests (nextest)
cargo clippy-strict     # Lint with -D warnings
cargo export-cards      # Run card data exporter
cargo coverage          # Card support coverage report
cargo wasm              # Build WASM (debug)
cargo wasm-release      # Build WASM (release)
cargo serve             # Run multiplayer server
cargo scrape-feeds      # Scrape metagame feeds

Project Structure

crates/
  engine/             Core rules engine
  engine-wasm/        WASM bindings
  phase-ai/           AI opponent
  server-core/        Server session management
  phase-server/       Axum WebSocket server
  feed-scraper/       Metagame deck scraper
client/               React frontend
scripts/              Build and setup scripts

Contact

Non-Commercial Fan Project

phase.rs is a non-commercial fan project built under the spirit of the Wizards of the Coast Fan Content Policy. It exists for hobbyist, educational, and research use only.

  • No bundled Wizards assets. This repository does not distribute MTG card images, card art, mana symbol artwork, card-frame graphics, or the Comprehensive Rules document. Card images and mana symbols are fetched from Scryfall at runtime by the user's browser. Card metadata is sourced from MTGJSON.
  • No affiliation. phase.rs is not affiliated with, endorsed by, sponsored by, or approved by Wizards of the Coast LLC or Hasbro, Inc.

Magic: The Gathering, Planeswalker, the mana symbols, and all associated names, text, and imagery are trademarks and copyrights of Wizards of the Coast LLC. All rights reserved by their respective owners.

If you believe content in this repository infringes your rights, please see DMCA.md.

Acknowledgments

License

Dual-licensed under MIT or Apache 2.0, at your option.

About

A Magic: The Gathering rules engine and game client — Rust + WASM + React

Topics

Resources

License

Apache-2.0, MIT licenses found

Licenses found

Apache-2.0
LICENSE-APACHE
MIT
LICENSE-MIT

Security policy

Stars

Watchers

Forks

Sponsor this project

 

Contributors