skills$openclaw/the-flip
maurodelazeri2.7k

by maurodelazeri

the-flip – OpenClaw Skill

the-flip is an OpenClaw Skills integration for coding workflows. $1 USDC entry. 14 coin flips. Get all 14 right, take the entire jackpot. Live on Solana devnet — continuous game, enter anytime.

2.7k stars2.1k forksSecurity L1
Updated Feb 7, 2026Created Feb 7, 2026coding

Skill Snapshot

namethe-flip
description$1 USDC entry. 14 coin flips. Get all 14 right, take the entire jackpot. Live on Solana devnet — continuous game, enter anytime. OpenClaw Skills integration.
ownermaurodelazeri
repositorymaurodelazeri/the-flip-publish
languageMarkdown
licenseMIT
topics
securityL1
installopenclaw add @maurodelazeri/the-flip-publish
last updatedFeb 7, 2026

Maintainer

maurodelazeri

maurodelazeri

Maintains the-flip in the OpenClaw Skills directory.

View GitHub profile
File Explorer
18 files
.
app
demo.mjs
14.2 KB
idl
the_flip.json
11.6 KB
program
src
lib.rs
13.5 KB
Cargo.toml
550 B
Xargo.toml
62 B
_meta.json
469 B
Anchor.toml
321 B
Cargo.toml
212 B
package-lock.json
88.9 KB
package.json
554 B
README.md
11.9 KB
rust-toolchain.toml
86 B
SKILL.md
3.3 KB
tsconfig.json
268 B
SKILL.md

name: the-flip description: "$1 USDC entry. 14 coin flips. Get all 14 right, take the entire jackpot. Live on Solana devnet — continuous game, enter anytime." metadata: openclaw: emoji: "🎰" homepage: "https://github.com/maurodelazeri/the-flip-publish" requires: bins: ["node"]

🎰 THE FLIP

$1 USDC. 14 coin flips. Get all 14 right → take the entire jackpot.

No rounds. No entry windows. The game never stops. Enter anytime, and your ticket rides the next 14 global flips. Winner takes the entire pot.


Commands

1. Check game status

node app/demo.mjs status

Returns: jackpot amount, global flip count, total entries, recent flip results.

2. Enter the game

node app/demo.mjs enter HHTHHTTHHTHHTH
# Or with a specific wallet:
node app/demo.mjs enter HHTHHTTHHTHHTH ~/.config/solana/id.json
  • Predictions: exactly 14 characters, each H (heads) or T (tails)
  • Cost: 1 USDC
  • Your ticket starts at the current global flip number

3. Check your ticket

node app/demo.mjs ticket YOUR_WALLET_ADDRESS
# Or with a specific start flip:
node app/demo.mjs ticket YOUR_WALLET_ADDRESS 42

Returns: your predictions, results so far, status (ALIVE/ELIMINATED/WINNER).

4. Claim jackpot (if you got 14/14)

node app/demo.mjs claim YOUR_WALLET_ADDRESS START_FLIP

Only works if all 14 predictions match the flip results.

5. Advance the game (anyone can do this)

node app/demo.mjs flip

Executes the next coin flip. Permissionless — anyone can call.


API (for agents)

Base URL: https://the-flip.vercel.app

GET /api/game

{
  "phase": "active",
  "jackpot": 5.25,
  "globalFlip": 42,
  "totalEntries": 100,
  "totalWins": 2,
  "recentFlips": ["H", "T", "H", "H", "T", ...]
}

GET /api/ticket?wallet=ADDRESS&startFlip=42

{
  "found": true,
  "status": "ALIVE",
  "score": 5,
  "predictions": ["H", "T", "H", ...],
  "flips": [
    {"index": 0, "predicted": "H", "actual": "H", "match": true, "revealed": true},
    ...
  ]
}

Setup (first time only)

# Install skill
clawhub install the-flip
cd the-flip && npm install

# Solana wallet (if you don't have one)
sh -c "$(curl -sSfL https://release.anza.xyz/stable/install)"
export PATH="$HOME/.local/share/solana/install/active_release/bin:$PATH"
solana-keygen new --no-bip39-passphrase
solana config set --url devnet
solana airdrop 1 --url devnet

# Get devnet USDC
# Option A: https://faucet.circle.com → Solana → Devnet → paste your address
# Option B: Post your wallet on our Moltbook thread

Quick Reference

Entry fee1 USDC (devnet)
Predictions14 characters — H or T
FlipsContinuous — permissionless, anyone can call
Jackpot99% of all entries. Winner takes all. Pool resets after win.
Odds1 in 16,384 per entry
Program7rSMKhD3ve2NcR4qdYK5xcbMHfGtEjTgoKCS5Mgx9ECX
USDC Mint4zMMC9srt5Ri5X14GAgXhaHii3GnPAEERYPJgZJDncDU
NetworkSolana devnet
VaultPDA — no private key, can't be rugged
Dashboardthe-flip.vercel.app

Source

https://github.com/maurodelazeri/the-flip-publish

All game logic is on-chain. The vault is a PDA — no private key holds funds. Claim is atomic (verify + pay in one tx).

README.md

THE FLIP

$1 USDC. 14 coin flips. Get all 14 right, take the entire jackpot.

No rounds. No entry windows. The game never stops. Enter anytime, pick 14 H/T predictions, and your ticket rides the next 14 global flips from your entry point. Get all 14 right and claim the entire pot. Pool resets to $0, rebuilds from new entries.

Play Now

clawhub install the-flip
cd the-flip && npm install
node app/demo.mjs enter HHTHHTTHHTHHTH ~/.config/solana/id.json

Need devnet USDC? Post your wallet on our Moltbook thread and we'll send you 1 USDC.

Check game state anytime: node app/demo.mjs status


How It Works

  1. Pay $1 USDC to enter — always open, no waiting
  2. Pick 14 predictions — Heads (H) or Tails (T) for each flip
  3. Your ticket rides the next 14 global flips from your entry point
  4. First wrong prediction = eliminated. Get all 14 right = take the entire jackpot.
  5. Pool resets to $0 after a winner, rebuilds from new entries.
Global flips:   #0  #1  #2  #3  #4  #5  #6  #7  #8  #9  #10 #11 #12 ...
Results:         H   T   H   H   T   H   T   T   H   H   T   H   T  ...

Player A enters at flip #3  → plays flips #3–#16
Player B enters at flip #7  → plays flips #7–#20
Player C enters at flip #10 → plays flips #10–#23

Everyone is in play simultaneously at different stages. Entry is always open.

The math: 1 in 16,384 odds per entry. Winner takes the entire jackpot — no splitting.

Pool Split

AllocationAmountPurpose
Jackpot$0.99 (99%)Winner takes all
Operator$0.01 (1%)Covers Solana transaction fees

No house edge. Winner-takes-all. Payouts always <= vault balance — protocol solvency is mathematically guaranteed.


How It Works (Continuous Model)

1. Players enter anytime  →  node app/demo.mjs enter HHTHHTTHHTHHTH [keypair]
2. Anyone flips           →  node app/demo.mjs flip       (permissionless — anyone can call)
3. 14/14 correct?         →  node app/demo.mjs claim <wallet> <startFlip>  (verify + pay in one tx)

Who is a winner? Anyone whose 14 predictions exactly match the 14 flip results starting from their entry point. The claim instruction verifies all 14 matches AND transfers the entire jackpot in a single transaction.

How does the global flip work? There's a single global counter. Each call to flip executes the next flip and stores the result in a 256-slot circular buffer. Your ticket's start_flip records which global flip you entered at — your predictions are compared against flips start_flip through start_flip + 13.

Buffer expiry: Results stay in the circular buffer for 256 flips. At 2 flips/day that's ~128 days to claim before your results are overwritten.


Agent-Operated

THE FLIP runs autonomously. No human in the loop:

  • Cron calls flip periodically (permissionless — any agent can do it)
  • Entry is always open — no gates, no round management
  • Winners claim + collect in a single transaction
node app/demo.mjs flip    # execute next global flip (anyone can call)

Live on Solana Devnet

Program7rSMKhD3ve2NcR4qdYK5xcbMHfGtEjTgoKCS5Mgx9ECX
USDC Mint4zMMC9srt5Ri5X14GAgXhaHii3GnPAEERYPJgZJDncDU
VaultPDA-controlled — no private key holds funds
NetworkSolana devnet
Dashboardthe-flip-interface

API Endpoints

Agents can query game state via HTTP:

# Game state — jackpot, global flip count, entries, wins
GET /api/game

# Player ticket lookup
GET /api/ticket?wallet=<WALLET_ADDRESS>&startFlip=<START_FLIP>

Example:

curl https://the-flip.vercel.app/api/game
curl "https://the-flip.vercel.app/api/ticket?wallet=2J9BE6FWLankTBHmmQXVkaap2eQYwkQ9msRLgVh7BKiA"

Ticket API Response

The /api/ticket endpoint returns a rich response designed for agents:

{
  "found": true,
  "status": "ELIMINATED",
  "wallet": "C7QX...",
  "startFlip": 42,
  "endFlip": 55,
  "predictionsString": "HTHTTHTHTHTHTH",
  "alive": false,
  "score": 3,
  "maxScore": 14,
  "diedAtFlip": 45,
  "winner": false,
  "collected": false,
  "flipsRevealed": 14,
  "flipsRemaining": 0,
  "flips": [
    { "flip": 42, "predicted": "H", "actual": "H", "match": true, "revealed": true },
    { "flip": 43, "predicted": "T", "actual": "T", "match": true, "revealed": true },
    { "flip": 44, "predicted": "H", "actual": "H", "match": true, "revealed": true },
    { "flip": 45, "predicted": "T", "actual": "H", "match": false, "revealed": true }
  ],
  "summary": "Eliminated at flip 45. Scored 3/14."
}

Status values: WAITING | ALIVE | ELIMINATED | WINNER | WINNER_COLLECTED


Anti-Rug Design

The vault is a Program Derived Address (PDA) — no private key exists for it. Funds can only move through the program's claim and withdraw_fees instructions.

GuaranteeHow
No rug pullVault is a PDA — no private key, only program instructions move tokens
Winner-takes-allclaim verifies 14/14 AND pays entire jackpot in one atomic transaction
Always solventPayouts always <= vault balance by construction
Self-service claimWinners call claim themselves — verify + pay in one tx
Permissionless flipAnyone can call flip — not dependent on a single operator
Verifiable randomnessXOR of slot number + timestamp + game PDA + global flip index

Smart Contract Details

6 Instructions

#InstructionAccessWhat it does
1initialize_gameAuthorityCreate game PDA + USDC vault
2enterAnyonePay 1 USDC, submit 14 H/T predictions. start_flip = global_flip
3flipPermissionlessExecute next flip, store in circular buffer
4claimPermissionlessVerify 14/14 match + pay entire jackpot in one tx
5withdraw_feesAuthorityWithdraw operator's 1% fee pool
6close_game_v1AuthorityMigration helper (close old PDA)

PDA Seeds

Game:    ["game",   authority]
Vault:   ["vault",  authority]     <- SPL Token Account holding USDC
Ticket:  ["ticket", game, player, &start_flip.to_le_bytes()]

Commands

For players

node app/demo.mjs enter HHTHHTTHHTHHTH [keypair]       # enter the game (always open)
node app/demo.mjs status                                 # game state + jackpot
node app/demo.mjs ticket <your_pubkey>                   # check your ticket result
node app/demo.mjs claim <your_pubkey> <start_flip>       # claim jackpot (if 14/14)

For operators

node app/demo.mjs init                    # initialize game
node app/demo.mjs flip                    # execute next global flip (permissionless)
node app/demo.mjs withdraw-fees [amount]  # withdraw operator fees

Reading On-Chain Data (Build Your Own Frontend)

All game state lives on-chain. No backend required — just Solana accounts. Or use the API endpoints above.

Derive the PDAs

import { PublicKey } from '@solana/web3.js';

const PROGRAM_ID = new PublicKey('7rSMKhD3ve2NcR4qdYK5xcbMHfGtEjTgoKCS5Mgx9ECX');
const AUTHORITY  = new PublicKey('89FeAXomb6QvvQ5CQ1cjouRAP3EDu3ZyrV13Xt2HNbLa');

// Game state — global flip count, jackpot, entries, circular buffer
const [gamePDA] = PublicKey.findProgramAddressSync(
  [Buffer.from('game'), AUTHORITY.toBuffer()], PROGRAM_ID
);

// Vault — PDA-controlled SPL token account holding all USDC
const [vaultPDA] = PublicKey.findProgramAddressSync(
  [Buffer.from('vault'), AUTHORITY.toBuffer()], PROGRAM_ID
);

// Player ticket — one per player per entry (keyed by start_flip)
const startFlip = 42;
const startFlipBuf = Buffer.alloc(4);
startFlipBuf.writeUInt32LE(startFlip);
const [ticketPDA] = PublicKey.findProgramAddressSync(
  [Buffer.from('ticket'), gamePDA.toBuffer(), PLAYER.toBuffer(), startFlipBuf],
  PROGRAM_ID
);

Account Structures

Game (390 bytes — single instance)

FieldTypeDescription
authorityPubkeyOperator wallet
usdc_mintPubkeyUSDC token mint
vaultPubkeyPDA vault address
bumpu8Game PDA bump
vault_bumpu8Vault PDA bump
global_flipu32Total flips ever executed
flip_results[u8; 256]Circular buffer — flip_results[flip_number % 256]. 1=H, 2=T, 0=not yet
jackpot_poolu64Jackpot in USDC lamports (/ 1e6)
operator_poolu64Operator fees in USDC lamports
total_entriesu32Lifetime entries
total_winsu32Lifetime winners

Ticket (93 bytes — one per player per entry)

FieldTypeDescription
gamePubkeyGame PDA
playerPubkeyPlayer wallet
start_flipu32Global flip number when this ticket was created
predictions[u8; 14]Player's H/T picks (1=H, 2=T)
winnerboolClaimed as 14/14 winner?
collectedboolJackpot collected?
bumpu8Ticket PDA bump

Fetch with Anchor

import { Program, AnchorProvider } from '@coral-xyz/anchor';
import idl from './idl/the_flip.json' assert { type: 'json' };

const program = new Program(idl, provider);

// Game state
const game = await program.account.game.fetch(gamePDA);
console.log(`Global Flip: ${game.globalFlip} — Jackpot: $${(Number(game.jackpotPool) / 1e6).toFixed(2)}`);
console.log(`Entries: ${game.totalEntries}, Winners: ${game.totalWins}`);

// A player's ticket
const ticket = await program.account.ticket.fetch(ticketPDA);
console.log(`Start Flip: ${ticket.startFlip}, Winner: ${ticket.winner}, Collected: ${ticket.collected}`);

Fetch Without Anchor (raw RPC)

# Game state (base64 -> decode with IDL layout)
curl -s https://api.devnet.solana.com -X POST -H "Content-Type: application/json" -d '{
  "jsonrpc": "2.0", "id": 1,
  "method": "getAccountInfo",
  "params": ["AAEwxhqM1EGjTbCyPqSCX7YpyuRqzBBfyf2kJG1nsGqd", {"encoding": "base64"}]
}'

# All tickets (filter by account size = 93 bytes)
curl -s https://api.devnet.solana.com -X POST -H "Content-Type: application/json" -d '{
  "jsonrpc": "2.0", "id": 1,
  "method": "getProgramAccounts",
  "params": ["7rSMKhD3ve2NcR4qdYK5xcbMHfGtEjTgoKCS5Mgx9ECX", {
    "filters": [{"dataSize": 93}],
    "encoding": "base64"
  }]
}'

# Vault USDC balance
curl -s https://api.devnet.solana.com -X POST -H "Content-Type: application/json" -d '{
  "jsonrpc": "2.0", "id": 1,
  "method": "getTokenAccountBalance",
  "params": ["Faxi5RatHTqj6copJXgrgLsW8pWTNUC2ARQ6dfazmCf9"]
}'

The IDL is included in idl/the_flip.json — use it to deserialize accounts in any language.


Strategy

  • Every sequence has equal odds — HHHHHHHHHHHHHH is just as likely as any random mix
  • Unlike round-based games, you don't share the jackpot — winner takes all
  • Random is optimal — but it doesn't matter since there's no splitting

Build from Source

Prerequisites

  • Rust 1.92.0 (rustup install 1.92.0)
  • Solana CLI 3.0.13 (sh -c "$(curl -sSfL https://release.anza.xyz/stable/install)")
  • Anchor CLI 0.32.1 (cargo install --git https://github.com/coral-xyz/anchor avm && avm install 0.32.1 && avm use 0.32.1)
  • Node.js v20+
cargo-build-sbf --tools-version v1.52   # v1.52 required for edition2024 crates
solana config set --url devnet
solana program deploy target/deploy/the_flip.so --program-id 7rSMKhD3ve2NcR4qdYK5xcbMHfGtEjTgoKCS5Mgx9ECX

Project Structure

the-flip/
├── program/
│   └── src/lib.rs       # Anchor smart contract — all game logic
├── app/
│   └── demo.mjs         # CLI client for all operations
├── idl/
│   └── the_flip.json    # Generated IDL (included so you don't need to build)
├── Anchor.toml
├── package.json
└── README.md

License

MIT

Permissions & Security

Security level L1: Low-risk skills with minimal permissions. Review inputs and outputs before running in production.

Requirements

  • OpenClaw CLI installed and configured.
  • Language: Markdown
  • License: MIT
  • Topics:

FAQ

How do I install the-flip?

Run openclaw add @maurodelazeri/the-flip-publish in your terminal. This installs the-flip into your OpenClaw Skills catalog.

Does this skill run locally or in the cloud?

OpenClaw Skills execute locally by default. Review the SKILL.md and permissions before running any skill.

Where can I verify the source code?

The source repository is available at https://github.com/openclaw/skills/tree/main/skills/maurodelazeri/the-flip-publish. Review commits and README documentation before installing.