Drop7 Research
← Learn

The D7P policy protocol

Chess engines speak UCI; Drop7 policies here speak D7P. The protocol is the contract that makes the leaderboard possible: wrap a strategy once, and any harness can drive it over the same predetermined rounds.

The shape of a policy

A policy answers exactly one question, using exactly four inputs:

// the only legal inputs

(board, nextDisc, movesUntilRise, gameOver)

column

Everything else — the seed, future discs, hidden gray-disc values, the score, the level, the move number — is privileged. Teachers may use privileged information to train a policy, but the deployed policy must play without it.

A wire session

Any language can speak D7P over stdin/stdout. A complete session looks like this:

-> d7p
<- id name Expectimax D2
<- id family fair-expectimax
<- id public-information true
<- d7pok
-> isready
<- readyok
-> position board 00000000000000000000000000000000000000008888888 next 4 rise 5
-> go
<- bestmove 3
-> quit

The board travels as a 49-character string: 0 empty, 17 numbered, 8 solid gray, 9 cracked gray, row-major from the top. bestmove answers with a 0-indexed column.

Try it against the registry

Every policy on the leaderboard ships with a D7P server:

node --experimental-strip-types src/bench/d7p-server.ts --policy greedy
d7p
isready
position startpos next 4 rise 5
go

Adding your own policy

  1. Implement chooseColumn(state) — see src/bench/policies.ts for the BenchPolicy interface and the existing registry entries.
  2. Keep it deterministic: the same public state must always produce the same column. Solver seeds derive from the policy id, never from game data.
  3. Register it, then run npm run bench -- --policies your-policy.
  4. If your policy reads level or move number, mark it publicInformation: false — it will be badged "extended state" on the leaderboard.

The normative specification lives in docs/d7p-protocol.md.