Purvakalpa Studio

Docs / Chess: Knight Fever

Wi-Fi play and security

Playing nearby devices with no server: joining by QR or four-letter code, Party Rooms and spectating, and what protects moves, identities and chat.

Knight Fever plays other devices on the same network directly, through Apple’s MultipeerConnectivity. There is no game server and no account: devices find each other on the local network and connect peer to peer. Both devices need the Local Network permission.

Starting a match

There are two ways in:

  • Host and join. The host opens a room, which shows a QR code and a four-letter code. The other player scans the QR code or types the code. The camera is used only to scan that QR code.
  • The lobby. A presence lobby lists every nearby device running the app, and each row has Challenge and Message buttons. If a challenge arrives while the app is in the background, a local notification names the challenger. There is no push server.

Joining does not depend on a single invitation getting through. After a code or a scan, the joining device rescans the network and re-invites the matching host about every four seconds, for up to about 80 seconds, and stops as soon as the connection opens.

Who owns the game

Play is host-authoritative: one device, the host, owns the game state, and the other devices connect to it. One source of truth makes cheating harder. A joining device introduces itself with its name, a player ID and a device ID, which also lets a device that drops be recognised when it reconnects.

The host also chooses the variant, Standard or Endless. When the match starts, the host sends the variant before it assigns roles, so the joiner knows which board to build before the first move arrives:

host                                       joiner
  |  variant (Standard or Endless)  ---->  |   joiner records the variant
  |  role                           ---->  |   both build the same match
  |  <---------------  moves  --------->   |

The variant message was added without changing the messages a standard game already used. Endless describes how Endless moves travel and how they are checked.

Party Rooms and spectating

A Party Room gathers up to eight devices around one board: two players, with everyone else watching live. Spectators see each move as it is played.

Every Wi-Fi match has Club Chat, with quick reactions, emoji and a mute switch. You can ping mid-game, and a live readout shows the connection’s latency. With voice features on, incoming chat and room events (joins, leaves and reconnects) are spoken, and spectators hear the matchup and each new move. See Coaching and accessibility.

When the connection drops

A standard match that loses its connection does not vanish. It is logged in your history as “Disconnected · unfinished”, where you can replay it, and the exact position is saved as a resumable two-player game. The Connection Lost screen offers Continue Offline to finish it on one device, and the game stays resumable from Home.

What protects what

DataProtection
Moves, chat and other messages during a matchMultipeerConnectivity’s encrypted session
Your name and IDs while devices discover and invite each otherSealed with ChaCha20-Poly1305 by SecureWire
Chat history stored on your deviceEncrypted at rest with ChaCha20-Poly1305, under a key that stays on the device
An exported chat recordA SHA-256 hash chain, signed with the device’s Ed25519 key

Before a session exists

MultipeerConnectivity encrypts a session once it is open. The steps before that, Bonjour discovery records and invitation contexts, are broadcast in the clear, so anything placed in them can be read by any device listening on the network. Knight Fever puts nothing there that a passive listener can read:

  • The peer name that discovery shows is a neutral handle such as “Knight-7F3A”, regenerated at every launch.
  • Your real name, player ID, device ID and iCloud status travel as one sealed token. SecureWire seals it with ChaCha20-Poly1305 under a key derived with HKDF-SHA256. Room invitations and rejoin requests are sealed the same way.
  • Every seal uses a fresh nonce, so the same identity never produces the same token twice and an observer cannot link one advertisement to the next.

Other devices running Knight Fever can open the token, which is how the lobby shows real names. A passive listener on the network sees only a neutral handle and an opaque value that changes every time.

The chat record

Club Chat history is kept as a record that can be handed over and checked, so a conversation can serve as evidence if it ever needs to.

  • ChatArchive keeps an append-only ledger of chat lines, up to 5,000 entries.
  • Each entry carries the hash of the one before it: a SHA-256 hash chain that starts from a fixed anchor. Editing, reordering or deleting any line breaks the chain, and verification reports it.
  • The ledger file is encrypted at rest with ChaCha20-Poly1305 under a random 256-bit key held in the Keychain, on this device only.
  • Export writes readable JSON with the participants, the full timeline with timestamps, the hash chain, an Ed25519 signature with its public key, and instructions for verifying it. The signing key belongs to the device and lives in its Keychain, so an export is attributable to the device that made it. On iPhone and iPad it goes to the share sheet; on the Mac, to a save panel.

Tests cover the chain verifying, an edited message breaking it, a reordered message breaking it, and the signature rejecting tampering.