Chess (Correspondence Chess Pro)

Correspondence chess app for two players. Originally created as “Correspondence-Chess-Pro,” the GitHub repo was renamed to “Chess” on 2026-02-12. Supports game sharing via plain-text codes (CHESS: prefix + PGN), move history with time-travel navigation, multiple board themes with dark mode, and customizable piece sets. No backend — fully client-side with localStorage persistence. Mobile-first PWA with iOS/iPad home screen install support.

Overview

Chess allows two players to conduct a correspondence game asynchronously. One player makes a move, exports a plain-text sync code, and shares it with their opponent via any messaging channel. The opponent pastes the code, views the board state, and makes their reply. No accounts, no servers, no third-party services.

The app was built with React + chess.js for complete move validation (checkmate, stalemate, en passant, castling). All game state lives client-side in localStorage.

Tech Stack

TechnologyVersionPurpose
TypeScript^5.6.0Primary language — strict mode enabled
React^18.2.0UI framework — functional components only
Vite^7.3.1Build tool and dev server (bumped from 5.0.8 for GHSA-67mh fix)
Tailwind CSS^3.4.1Utility-first CSS styling
chess.js^1.4.0Chess engine — FEN/PGN parsing, move validation
Vitest^2.0.0Unit testing framework (jsdom environment)
ESLint^9.39.2Code linting (flat config format)
Node.js>=18.0.0Runtime environment

Deployment: Static site via Vite build. Vercel-ready (vercel.json configured, auto-deploy on push). No backend required.

Architecture

src/
  App.tsx                    # Root component — game state, move handling
  components/
    Board.tsx                # FEN parsing, square rendering, tap-to-move input
    Piece.tsx                # Piece rendering with piece set selection
    HistoryControls.tsx      # Move history navigation (first/prev/next/last)
    StatusIndicator.tsx      # Game status (check, checkmate, draw)
    QRCodePanel.tsx          # QR code generation for game sharing (dormant)
  services/
    syncCode.ts              # Plain-text game code encode/decode (CHESS: + PGN)
  utils/
    storage.ts               # localStorage wrapper for game persistence
    logger.ts                # Console logging utility
Components/                  # Legacy directory (partially migrated to src/)

State management: React hooks (useState, useMemo, useCallback) in App.tsx. chess.js Chess instance as primary game state. viewingIndex: null = current position; a number = historical position. After a 2026-03-13 refactor, App.tsx was reduced to ≤100 lines by extracting a SyncPanel component, useGameState hook, and Icons.

Game sharing: Sync codes are plain-text strings with a CHESS: prefix followed by PGN. Human-readable, copy-paste friendly, works over any channel.

Key Decisions and Patterns

  • Tap-to-move over drag-and-drop — better for mobile touch targets (44px HIG compliance). See localstorage-persistence-with-zod-validation for a related client-side persistence pattern.
  • CSS custom properties for board themes — runtime theme switching without React re-render, controlled via data-board-theme HTML attribute.
  • IIFE in index.html for theme init — prevents flash of wrong theme on page load.
  • Tailwind class-based dark mode — user-controlled toggle rather than CSS media query.
  • chess.js for all move validation — no manual FEN parsing; proven library handles all rules, FEN, and PGN.
  • Plain-text game codes — simplest possible sync mechanism, no encryption, human-readable.
  • Module-export services (not class-based) — syncCode.ts structured as plain exports for tree-shaking. See module-export-services-not-class-based.
  • Stripped encryption — MVP testing does not need security complexity; dormant BIP-39 and idb-keyval modules inherited from original codebase remain unused.
  • Vite bumped to 7.3.1 — resolved GHSA-67mh esbuild dev server vulnerability.

Current Status

Version: v1.1 shipped; v1.2 in progress Phase: v1.2 Phase 10 — Link & QR Sharing (active as of 2026-03-13) CI/CD: Passing Test coverage: 60-70% (core logic covered; App.tsx and Board.tsx have no tests) Linear Project: Aloysius Productions GitHub: irishrocker1125/Chess

v1.2 roadmap defines 3 phases and 11 requirements:

  1. Phase 10 — Link & QR Sharing (SHARE-01/02/03)
  2. Phase 11 — Multi-Game Management (GAME-01/02/03/04)
  3. Phase 12 — Interaction & Polish (INTX-01, UX-01/02/03/04)

Technical Debt

ItemPriorityNotes
localStorage/IndexedDB dual storageMediumDual backends — unclear source of truth
No tests for App.tsx or Board.tsxMediumCore game logic untested
Mixed directory structure (Components/ vs src/)LowLegacy and new structure coexist
Unused CCP-era utilitiesLowBIP-39, idb-keyval, QRCodePanel — dormant
as any type cast in Board.tsxLowBypasses type safety for piece types