STATUS · Built and tested locally. Not a public network. No public node. Mainnet anchoring waits on a funded key. First Mints and the art certificates are previews or rehearsals.

CHAIN · DEV TOOLS · SOURCE da7bc09 · LOCAL TODAY

Run the chain on your machine.

Everything here runs on a laptop. The repo is local today and has no public remote, so there is no clone URL on this page; the steps assume you have a copy. Dev chains use public keys, so nothing on one has value.

quickstarthttp apimcpclisdkdocsverify deskproof of balanceart mirror

01 · QUICKSTART · RUST VIA RUSTUP

Five steps to a running town.

1 · Install Rust (stable), if you don’t have it

curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y --profile minimal

2 · Run the tests, core first

cargo test -p chain-core
cargo test --workspace
(cd crates/kernel && cargo test)   # the rollup kernel is its own workspace

3 · Start a dev chain with synthetic traffic

cargo run -p node -- run --dev --demo

--dev uses publicly derivable keys. --demo adds two humans, a tz2 human, two agents (Frog and Sparrow) and the MCP agent (Wire Desk), then generates taps, posts, drum sessions, drop mints and transfers.

4 · Open what it serves

OpenWhat you see
http://127.0.0.1:8545/The explorer. Press ✓ VERIFY and your browser replays the chain.
/statusHeight, tip, state root, supply, chain id and genesis hash.
/metricsPrometheus text for the night shift.
/readyz200 while blocks are fresh; 503 when the tip is older than 9 seconds.

5 · Add Town Hall, following the node from step 3

cargo run -p pointcast-town -- --node http://127.0.0.1:8545
# Town Hall  http://127.0.0.1:8550/   (also /hall)
# API        http://127.0.0.1:8550/api/town/status

Or, with nothing else running, scripts/town-demo.sh starts its own --dev --demo node and pc-town on throwaway databases and removes them on Ctrl-C. It refuses to start if something already answers on 8545 or 8550, so stop the step 3 node first. pc-town holds no keys.

Then · let an agent in, and ask the doctor

claude mcp add --transport http pointcast-chain http://127.0.0.1:8545/mcp
claude mcp add --transport http pc-town http://127.0.0.1:8550/mcp
cargo run -p node -- doctor --db data/chain.sqlite   # a dev chain is NOT READY, and it says why

02 · HTTP API · 33 ROUTES ON THE NODE · 15 ON PC-TOWN

Every route, from the route declarations.

The node listens on 127.0.0.1:8545 by default and pc-town on 127.0.0.1:8550. Both send permissive CORS. File names are under crates/node/src/ and crates/town/src/.

pointcast-node · 33 routes
MethodPathReturnsFile
GET/The explorer: the chain as a PointCast-style feed, with VERIFY and the Transmit wallet panel.api.rs
GET/statusHeight, tip, state root, supply, counts, chain_id and genesis_hash.api.rs
POST/txSubmit a SignedTx (JSON) → {tx_hash}.api.rs
POST/tx/digestUnsigned tx → the raw digest, plus the wallet message and Micheline payload to sign.api.rs
POST/drum/digestDrum session claim → attestation digest and per-player co-sign payloads. Sizes are bounded before the node lock.api.rs
GET/tx/{hash}pending · included (with receipt) · rejected (with reason).api.rs
GET/block/latestThe newest block with tx cards.api.rs
GET/block/{height}One block with tx cards.api.rs
GET/account/{address}Balance, nonce, next_nonce (counts the mempool), agent info, drops.api.rs
GET/feedNewest blocks first. ?limit=20&before=H&all=false; all=true includes empty blocks.api.rs
GET/anchorsRecent anchor payloads and their status.api.rs
POST/bodyStore a block body off chain (at most 64 KiB) → {body_hash}.api.rs
GET/body/{hash}Body text.api.rs
POST/mcpThe MCP server (JSON-RPC 2.0, streamable HTTP). GET answers 405.api.rs
GET/metricsPrometheus text: height, block age, mempool depth, txs and ATTN by kind, supply, accounts at the epoch cap, top-10 issuance share, anchors by status, db bytes.ops.rs
GET/healthzok, unless the node lock is poisoned.ops.rs
GET/readyz503 when the tip is older than PC_READY_MAX_BLOCK_AGE_MS (default 9,000).ops.rs
GET/paramsGenesis params; blake2b(params) is /status.genesis_hash.api_raw.rs
GET/raw/block/{height}The exact serde Block, every signature included (404 if missing).api_raw.rs
GET/raw/blocks?from=H&limit=N → {tip, from, blocks}, ascending, N ≤ 500.api_raw.rs
GET/verifier/pointcast_chain.wasmThe verifier wasm.api_raw.rs
GET/verifier/pointcast_chain.wasm.sha256Its committed sha256.api_raw.rs
GET/verifier/verify.jsThe page-side verifier wrapper.api_raw.rs
GET/verifier/verify-worker.jsThe Web Worker that replays blocks.api_raw.rs
GET/proof/account/{addr}An unsigned proof at the tip.proofs.rs
GET/proof/claim/{addr}?height=H → a balance claim at a retained anchor; 404 “replay required” once the snapshot is gone.proofs.rs
GET/agent/{addr}/mandateThe agent’s mandate as the next block sees it, or 404 {"mandate": null}.api_mandate.rs
GET/drops?prefix&creator&after&limit → drops sorted by id, with creator, minted and remaining.api_art.rs
POST/drops/prepare-mintAn unsigned drop_mint with advisory checks and the wallet payload. Refuses to create a drop unless create:true.api_art.rs
GET/drop/{id}One drop: creator, minted, chain cap, remaining, first height.api_art.rs
GET/drop/{id}/mintsMints in chain order. Editions can’t move, so this is the holder list.api_art.rs
GET/account/{address}/drops?at=tip|anchor&height&drop → editions held, with a chain-proof claim.api_art.rs
POST/tx/simulateRun a SignedTx through the real apply_tx on a copy of the tip.api_art.rs
pc-town · 15 routes · read only
MethodPathReturnsFile
GET/Town Hall (#/ square, #/a/{addr}, #/c/{code}, #/r/{room}, #/b/{h}).api.rs
GET/hallThe same page.api.rs
GET/api/town/healthok, halted, or a fault with its evidence; 503 when not ok.api.rs
GET/api/town/statusVerified height, state root, supply, counts, recent state roots.api.rs
GET/api/town/accountsThe register.api.rs
GET/api/town/account/{addr}Balance, the epoch ATTN tank, tap window, agents, mandate, attestations, first page of txs.api.rs
GET/api/town/account/{addr}/txs?before=H&role=R → older txs, with the account’s roles in each.api.rs
GET/api/town/channelsChannels.api.rs
GET/api/town/channel/{code}One channel’s posts. ?before=Hapi.rs
GET/api/town/roomsRooms.api.rs
GET/api/town/room/{room}Sessions, attestation mix, credited-seconds leaderboard this epoch.api.rs
GET/api/town/blocksRecent blocks. ?busy=trueapi.rs
GET/api/town/block/{h}A replayed block with its txs and receipts.api.rs
GET/api/town/body/{hash}The node’s body, re-hashed; 502 if it doesn’t match body_hash.api.rs
POST/mcpRead-only MCP. GET answers 405.api.rs

Signatures bind the chain’s genesis hash as well as its id, so take both from GET /status before you sign.

03 · MCP · 6 TOOLS ON THE NODE · 4 ON PC-TOWN

Agents use the same chain.

Write tools take a client-signed signed_tx (preferred: the agent holds its own key) or plain fields that the node signs as its custodial agent. /mcp has no caller auth, so the custodial path refuses any request that carries an Origin header.

  • POINTCAST-NODE · mcp.rs

    • post_blockPublish a PointCast Block on chain. The node stores the body off chain; the chain records its hash.
    • drum_sessionRecord a finished drum session. Players earn capped ATTN only if attested: the sender always, others by co-signature or a room attestation.
    • get_feedNewest blocks first, with transaction cards.
    • my_mandateThe owner-granted mandate bounding an agent: kinds, channels and rooms, allowance left, payees, blocks until expiry.
    • spend_allowancePay ATTN from the agent’s owner’s balance, within the mandate’s caps and payee list. The custodial path refuses browser requests.
    • prove_balanceA portable balance claim: the sealed tip, or a retained anchor at a given height. Verify offline with the genesis params.
  • PC-TOWN · mcp.rs · READ ONLY

    • town_statusThe town square from pc-town’s own replay, with health.
    • town_accountOne account as pc-town replayed it: balance, epoch tank, tap window, agents, mandate, newest txs.
    • channel_feedA channel’s posts, newest first.
    • room_sessionsA room’s drum sessions, attestation mix and this epoch’s leaderboard.

04 · CLI · POINTCAST-NODE · PC-SIM · PC-TOWN

13 subcommands, and two more tools.

pointcast-node (crates/node/src/main.rs)
CommandUsageWhat it does
runrun [--dev] [--demo] [--db PATH] [--addr HOST:PORT] [--block-ms N]Start the sequencer. On restart it replays every stored block and re-checks signatures and roots.
keygenkeygen [--secp256k1]A new key, its tz address and its agent address. Store the secret in a secret manager.
signsign --nonce N [--agent | --wallet] --chain ID --genesis HEX '<tx kind JSON>'Sign a tx with PC_SIGNER_SECRET; --wallet produces what Kukai or Temple return.
attest-drumattest-drum --as player|room [--mode raw|wallet] …Print a drum co-signature or room attestation.
presence-ticketpresence-ticket --login ID --holder ADDR --room R …Sign a presence ticket locally, as a reference issuer.
anchoranchor status|reveal|post|verify|keygenTezos anchoring. Only post --yes signs and spends tez.
evidenceevidence check <evidence.json> --params <params.json> | evidence params --db PATHCheck sequencer-fault evidence offline. Exit 0 is a proven fault, 1 is not evidence.
proveprove <addr> [--height H] [--db PATH]Export a balance claim (Proof of Balance).
verify-claimverify-claim <claim.json> --params <params.json> [--genesis HEX]Verify a claim offline. Prints PROVEN and exits 0, or exits 1.
doctordoctor [--db PATH] [--json] [--allow-dev]Offline launch checks. Prints PASS, WARN or FAIL lines, then READY or NOT READY (exit 1).
backupbackup --db SRC --out DSTA consistent snapshot of the database.
restorerestore --from BACKUP --db DST [--verify] | restore --verify-only BACKUPRestore, proven by a full replay with --verify.
artart mirror|create|setup-dev|house|status|submit|record-fixtureThe pointcast-chain side of a 1 tez Tezos art sale. Without --yes nothing is signed.
  • PC-SIM · THE ECONOMY SIMULATOR

    pc-sim run <scenario.json> [--days N] [--seed N] [--out DIR]
    pc-sim sweep <scenario.json> --grid key=v1,v2 [--grid …]
    pc-sim bounds [scenario.json]

    Scenario output, not a forecast. Each run prints seed → root and writes summary.json, days.csv and a self-contained report.html.

  • PC-TOWN · TOWN HALL

    pc-town [--node URL] [--genesis HEX]
            [--db PATH] [--addr HOST:PORT]

    Follows a node, replays every block with the real verifier, and serves Town Hall. --genesis pins the chain and refuses a node that serves another one.

Scripts: scripts/town-demo.sh, scripts/art-demo.sh, scripts/build-verifier.sh, scripts/pin-verifier.sh. Examples: cargo run -p node --example lying_node and --example proof_demo.

05 · SDK · ONE FILE · ZERO DEPENDENCIES · BROWSER AND NODE 20+

pointcast-chain.js

One ES module that mirrors chain-core byte for byte: the test vectors are generated from Rust, and the Rust side refuses to drift from them. It reads drops and holders, verifies ownership claims locally, and has a Tezos wallet sign through Beacon only after rebuilding the payload itself. It is published here unchanged from the repo.

Download pointcast-chain.js 48 KB · ES module · MIT, per its package.json · from da7bc09

Read · connect, read a drop, check holdings

import * as pcc from "https://pointcast.xyz/chain/sdk/pointcast-chain.js";

// 1. Connect, and pin the chain you expect (from your own config, not the node).
//    With no node, connect(null) gives a client whose reads return {status: "no_node"}.
const chain = await pcc.connect("http://127.0.0.1:8545", {
  expect: { chainId: "pointcast-dev", genesisHash: GENESIS_HASH },
});

// 2. Read a drop and its holders. Editions can't move, so the mints are the holders.
const drop = await chain.getDrop("coffee-mug-0");
const mints = await chain.getMints("coffee-mug-0");

// 3. Check holdings. The claim is verified in your browser: Merkle path, sequencer seal, pinned genesis.
const h = await chain.getHoldings("tz1…", { drop: "coffee-mug-0" });
h.verification.verifiedHolder;  // false on any --dev chain, by design
h.verification.holderReason;    // why not

Sign · for the creator’s desk

// For the creator's desk, not a public gallery. The creator's Kukai signs.
const tx = await chain.buildDropMint({ sender: creatorTz2, dropId: "coffee-mug-0", recipient: buyer });
const prepared = await chain.digest(tx);     // throws unless the node's digest equals the local rebuild
// Kukai shows only kind, sender, nonce and digest: show the creator your own summary of tx first.
const signed = await chain.signWithBeacon(dAppClient, prepared);
await chain.simulate(signed);                // optional dry run on the real state machine
const { txHash } = await chain.submit(signed); // throws unless the node reports the local tx id
await chain.waitForTx(txHash);

There is no public node, so a gallery today calls pcc.connect(null) and renders pcc.certificateCopy("no_node"): “PointCast chain: local rehearsal only. No certificates are issued or promised.” Only verification.verifiedHolder may earn a badge, and it needs a named drop, a genesis pinned by the caller, a verified claim and a chain that isn’t a dev chain. In Node, download the file and import it from disk.

Pure exports include blake2b, sha256, addressKind, recipientStatus, encodeTx, signingHash, walletText, txHash, bodyHash, paramsHash, checkDropId, verifyClaim, verifyOwnership and certificateCopy.

06 · DOCS · COPIED FROM THE REPO AT da7bc09

Read the design in full.

  • The README.Quick start, environment, the HTTP API, signing with Kukai and Temple, drum attestation, MCP, Town Hall, VERIFY, the simulator, proofs and Tezos anchoring with measured costs.
  • The design notes.The shape of the chain, the determinism rules, accounts and signing modes, every transaction kind, drum attestation, mandates, presence tickets, the state root, the trust model, known gaps and the path to a Tezos rollup kernel.
  • v2: Present Company.The v2 plan: four pillars, fourteen packages over seven batches, batch-1 ownership, the demo moment, risks and merge order. Batch 1 is merged; its batch 2–7 list has since been replaced by the Town Network plan.
  • Wallets, one profile, passkeys and First Mints.A research and design document, not built code: passkeys as a pass, device passes, one profile, the webauthn signing mode, First Mints recipes, phases and the open questions for Mike.
  • Art minting.The pointcast-chain side of the dual-chain gallery: what is possible, the recommendation, the flow, the read API, the SDK, the mirror CLI, failure handling and the steps that need Mike. Local rehearsal.
  • pc-sim findings.What the economy simulator measured over 123.1 million applied transactions: every sybil key earns the epoch cap, and only room-attested drums plus tap gating together cut farming from 66% to 10.1%.
  • Independent review by Codex.Seven findings, each with a test that failed before the fix, and six follow-ups from Claude’s adversarial pass. Written by Claude from Codex’s tests and notes after OpenAI’s content filter stopped the run.
  • Proof of Balance: Codex’s report.What Codex built, how it validated it, the requirement it proved impossible (leaf counts are not authenticated) and the socket-free demo it ran when the sandbox blocked a port.

07 · VERIFY DESK AND EVIDENCE

Catch a lying node on purpose.

VERIFY downloads the consensus code, pinned by sha256, and replays every block in a Web Worker. Only faults that carry checked evidence are blamed on the sequencer, and the evidence is portable: anyone with the chain’s params can check it offline. The demo node re-seals a tampered state root at #37.

cargo run -p node --example lying_node      # 127.0.0.1:8546, local only
# with the dev node still on 8545, open http://127.0.0.1:8545/?api=http://127.0.0.1:8546
# press VERIFY, then download evidence.json from the red banner
curl -s http://127.0.0.1:8546/params > params.json
pointcast-node evidence check evidence.json --params params.json   # exit 0 = proven fault, 1 = not evidence

08 · PROOF OF BALANCE · VERIFY-CLAIM

Prove a balance without replaying history.

A claim ties an account to a state root that the sequencer signed in an anchor or a sealed header, bound to the genesis. Verification runs offline and prints its scope: inclusion in a sequencer-signed root, not transition validity or Tezos finality. Built by Codex.

pointcast-node prove <address> --height 200 --db data/chain.sqlite > claim.json
pointcast-node verify-claim claim.json --params params.json --genesis <trusted-genesis-hash>

09 · THE ART MIRROR · LOCAL REHEARSAL

Check a Tezos sale before anything is signed.

After a 1 tez sale on Tezos, the mirror checks the operation (applied, two successor blocks, the payment, the token transfer from a house seller) and only then plans a free first-collector certificate on pointcast-chain. Without --yes nothing is signed or journaled. No certificate has been issued, and none is promised.

pointcast-node art mirror --tezos-op <op-hash> --contract KT1… --token-id 0 \
    --pay-to KT1… --seller tz2… --drop coffee-mug-0 --db data/art-mirror.sqlite   # plan only
scripts/art-demo.sh                                                                # live smoke on 127.0.0.1:8596, dev keys