clone

two-player chess in the terminal, kept in a shared sqlite file and played with gum

main
select-mate.sh / README.md
README.md 6.0K rendered
1# select-mate.sh23`select-mate.sh` is a terminal chess game backed by SQLite. It uses [`gum`](https://github.com/charmbracelet/gum) for the interactive picker UI, stores game state on disk, supports named identities, and can point at a board/database URI from stdin. The fun part is that two players can open the same `game.db` from different terminals, or even different machines, as long as they both see the same shared filesystem path.45## Requirements67- `bash`8- `sqlite3`9- `curl` if you want to run it directly from `https://select-mate.sh`10- `gum` for the richer picker UI, optional1112On macOS with Homebrew:1314```bash15brew install sqlite gum16```1718If you skip `gum`, the game falls back to plain terminal prompts and numbered menus.1920## Quick Start2122Run the hosted script in one shot:2324```bash25curl -fsSL https://select-mate.sh | sh26```2728The URL should serve the actual released `select-mate.sh` script. When launched this way, the script hops into `bash`, reattaches to your terminal for prompts, asks for your identity, and then lets you choose between a multiplayer game and a local-only game.2930Make sure the script is executable:3132```bash33chmod +x ./select-mate.sh34```3536Start or resume the active game:3738```bash39./select-mate.sh40```4142Set a default identity in standard XDG config:4344```bash45mkdir -p "${XDG_CONFIG_HOME:-$HOME/.config}"46printf 'identity=alice\n' > "${XDG_CONFIG_HOME:-$HOME/.config}/select-mate.conf"47```4849Print the currently selected identity:5051```bash52./select-mate.sh --whoami53```5455Start a fresh multiplayer game:5657```bash58./select-mate.sh --new59```6061Start a fresh local game where one identity controls both sides:6263```bash64./select-mate.sh --local65```6667Show the move history for the active game:6869```bash70./select-mate.sh --moves71```7273Target a specific board/database by piping a URI on stdin:7475```bash76printf 'file:/tmp/select-mate.db?mode=rwc\n' | ./select-mate.sh --whoami77```7879Show CLI help:8081```bash82./select-mate.sh --help83```8485If you are hosting the curl entrypoint yourself, serve the exact released `select-mate.sh` script at `https://select-mate.sh`.8687For a shared live-test setup with two terminals:8889```bash90make alice91make bob92```9394## Identity Selection9596Identity comes from the first available source in this order:9798- `--identity NAME`99- `${XDG_CONFIG_HOME:-$HOME/.config}/select-mate.conf`100- the selected identity already remembered in the active board database101102When an identity is provided explicitly or via config, it is used for the current client session without rewriting the board's remembered identity. If you use the in-app identity picker, that choice is remembered in the board database and reused on the next launch when no `--identity` or config override is supplied.103104Config format is a single key/value entry:105106```bash107identity=alice108```109110If you do not pipe a board URI on stdin, game state is stored next to the config file by default:111112```bash113${XDG_CONFIG_HOME:-$HOME/.config}/game.db114```115116If you want an isolated game state for testing, point `XDG_CONFIG_HOME` somewhere else:117118```bash119XDG_CONFIG_HOME="$(mktemp -d)" ./select-mate.sh120```121122## Multiplayer123124Multiplayer is board/database based: Alice and Bob can both point at the same SQLite `game.db` and watch turn ownership switch live.125126The main flow to show off is a shared database on a network-mounted folder. This is still SQLite, not a separate server process, so both machines need the same shared filesystem and working SQLite file locks.127128Example shared location:129130```bash131/Volumes/chess-share/select-mate/game.db132```133134Alice on one machine:135136```bash137mkdir -p "${XDG_CONFIG_HOME:-$HOME/.config}"138printf 'identity=alice\n' > "${XDG_CONFIG_HOME:-$HOME/.config}/select-mate.conf"139printf 'file:/Volumes/chess-share/select-mate/game.db?mode=rwc\n' | ./select-mate.sh --new140```141142Bob on another machine with the same network share mounted:143144```bash145mkdir -p "${XDG_CONFIG_HOME:-$HOME/.config}"146printf 'identity=bob\n' > "${XDG_CONFIG_HOME:-$HOME/.config}/select-mate.conf"147printf 'file:/Volumes/chess-share/select-mate/game.db?mode=rwc\n' | ./select-mate.sh148```149150What that looks like in practice:151152- Alice starts a new multiplayer game and assigns `alice` / `bob`.153- Bob opens the same shared `game.db` and immediately lands in the same match.154- The side to move gets the writable action list.155- The other player sees a read-only waiting screen, but can refresh and inspect moves.156- After each move, the other terminal can refresh and take over from the same shared board state.157- You can keep both terminals open the whole time, which makes the turn handoff very visible.158159If you want to demo the same idea on one machine first, the repo includes a `Makefile` that pins both players to the same board URI under `/tmp/select-mate-live`:160161```bash162make alice163make bob164```165166Recommended live-test flow:167168- Run `make alice` in one terminal.169- Run `make bob` in a second terminal.170- Start a new multiplayer game from one side and assign `alice` / `bob`.171- Keep both terminals open to see writable vs read-only mode change live after each move.172173Helper targets:174175- `make test-prepare` creates the shared board/config layout.176- `make test-board-uri` prints the shared board URI.177- `make test-reset` removes the shared `/tmp/select-mate-live` test area.178179For multiplayer with separate config homes or identities, pipe the shared board URI on stdin:180181```bash182printf 'file:/tmp/select-mate-shared/game.db?mode=rwc\n' | ./select-mate.sh --identity alice183printf 'file:/tmp/select-mate-shared/game.db?mode=rwc\n' | ./select-mate.sh --identity bob184```185186Recommended flow:187188- One player starts the game with `./select-mate.sh --new` and assigns white/black identities.189- Both players open the same board path.190- Only the identity assigned to the side to move gets write actions.191- The other identity sees a read-only waiting view and can still refresh and inspect moves.192- Choose the player identity up front with `--identity NAME` before joining a multiplayer board.193194Current limitations:195196- Avoid trying to make moves at the same time from two terminals.197- The stdin contract is one raw board URI line, not JSON or key/value input.