Official Psy project templates for Psy Protocol.
Maturity Status:
psy-templateis currently in the convergence stage from proof-of-concept toward a high-determinism safe subset, and is NOT mainnet production ready.
Designed for use with psyup new.
For a full breakdown of the ZK-native partitioned state model, Plonky2 Goldilocks arithmetic, Outbox/Claim protocols, and stated security invariants, see the Design Specification.
For release blockers and acceptance criteria, see Production Readiness Gates.
For the current engineering handoff, see PSY-20 / PSY-721 handoff (2026-09-24).
| Template | Path | Description | Command |
|---|---|---|---|
| dapp (default) | dapp/ |
Full-stack React + Vite frontend with a Psy token contract in contract/ |
psyup new my-app |
| token | token/ |
Pure PSY-20 Fungible Token contract (Phase 1 Safe Subset: liquid balance, Outbox Transfer/Claim, Batched Transfers, strict Goldilocks arithmetic) | psyup new my-token --template token |
| nft | nft/ |
PSY-721 v3 NFT contract (computational namespace uniqueness, slot storage, four-slot Outbox with explicit ACK) | psyup new my-nft --template nft |
To install or update the Psyup toolchain:
# Install psyup and core ZK compiler binaries
curl -fsSL https://raw.githubusercontent.com/PsyProtocol/psyup/main/install.sh | bash
# Ensure ~/.psy/bin is in your PATH
export PATH="$HOME/.psy/bin:$PATH"# Fullstack dApp with React UI + contract (default)
psyup new my-app
# Pure PSY-20 Fungible Token Contract
psyup new my-token --template token
# Pure PSY-721 NFT Contract
psyup new my-nft --template nftAsset issuance is locked to a compile-time designated partition (ISSUER_USER_ID). The legacy token and NFT sources also check the deployer public key. The staging-compatible NFT v3 compiler does not expose that intrinsic; its NFT contract checks the canonical user ID on chain and its deployment script verifies the selected wallet against the registered ID.
The issuer user ID must be in 1..16777215. Outbox arrays have 24-bit indices; a larger issuer ID could mint assets but could not transfer them.
Warning
You MUST configure ISSUER_USER_ID to match your actual on-chain account's user_id before building and deploying. If deployed with a mismatched ID, the contract will permanently reject initialization and minting from your account, bricking the deployment.
# Set canonical ISSUER_USER_ID to your registered on-chain user ID:
npm run configure -- --issuer <YOUR_USER_ID>
# Strict deployment preflight check (verifies explicit configuration record via .issuer_configured):
npm run check:preflightNote
Deployment boundary: Root check:preflight verifies the configured source and local marker. Each standalone template also provides check:deployer and deploy:checked, which query the selected wallet's first registered user ID on the configured network. Direct psyup deploy bypasses these checks.
Inside any contract directory (or project root for pure contract templates):
# Build with deployment preflight check (blocks compilation if unconfigured):
npm run build:deploy
# Or standard build:
npm run buildThe token template has a complete legacy .psy source, a public-only v3 source, and a private-enabled v3 source. The private v3 profile requires an isolated compiler build and completed a two-user staging round trip on contract 53. Both v3 profiles include name/URI metadata, an optional immutable lifetime cap, mint_to, and issuer settlement of holder burns into total_supply. A burn remains counted until settlement. The NFT staging build uses psy_user_cli compile; the dApp contract remains on the psyup build path. See the token guide and NFT guide for commands and limits.
From the token/, nft/, or dapp/ template directory, set exactly one of PRIVATE_KEY or KEYSTORE_PATH (plus WALLET_PASSWORD for a keystore) and set RPC_CONFIG for the intended network. Then run:
npm run check:deployer
npm run deploy:checked # NFT and dApp
# From token/, for a public-only staging token:
npm run deploy:staging-public
# From token/, for the private-enabled v3 profile with its matching compiler:
PSY_PRIVATE_CLI=/path/to/psy_user_cli npm run deploy:private-v3deploy:checked checks the selected wallet's registered issuer ID. For the token template it stops because the default v3 artifact omits private methods. Use deploy:staging-public only for an explicit public-only token, or deploy:private-v3 with the matching isolated compiler. For NFT, deploy:checked submits the v3 artifact. Direct psyup deploy bypasses the issuer wallet checks.
Each template includes a comprehensive, step-by-step operational guide:
-
PSY-20 Token Guide:
-
High-Determinism Safe Subset: Liquid balance management,
mint,burn,transfer,claim,batch_transfer_2,batch_transfer_5. -
Edge RPC Slot Reading: Zero-gas, direct storage slot queries (
getUserContractStateTreeLeafHash) for balances and Outbox state. - Monotonic Outbox/Claim: High-concurrency pull payments immune to stale-read double-spending.
-
Goldilocks Prime Field Arithmetic: Strict
$p - 1$ bounds preventing modular wrap-around. - Cooperative Delegation: 16 independent escrow slots; spender-local terminal close before owner refund. Owner-only instant revocation is unavailable on the current protocol.
-
High-Determinism Safe Subset: Liquid balance management,
-
PSY-721 NFT Guide:
-
Computational Namespace Uniqueness:
Poseidon(creator, local_id)providing collision-resistant token identity. - Slot-Based Ownership: Unique token slot management up to 128 slots.
- Sliding Window Outbox & Explicit ACK: Separate inbound and outbound counters support two-way transfers; the sender acknowledges claims before reusing full queue capacity.
-
Computational Namespace Uniqueness:
-
Full-Stack dApp Guide:
-
Vite + React Integration: Browser extension connection via
window.psy. -
SDK Builders: Strongly-typed transaction construction via
@psy-protocol/psy-sdk.
-
Vite + React Integration: Browser extension connection via
-
Design Specification:
- Formal mathematical invariants, Plonky2 Goldilocks arithmetic, state partitioning axioms, and cooperative delegation settlement limits.
The repository includes legacy native ZK contract unit tests, staging v3 compilation and ABI checks, and JavaScript multi-user state simulations. A separate staging report records real multi-user cross-realm NFT transactions. The legacy dargo NFT unit harness does not execute the v3 source:
# Run the complete test matrix (Unit + E2E + Adversarial)
npm test
# Run native Plonky2 ZK contract unit tests via dargo test
npm run test:unit
# Run multi-user state and invariant simulations plus compilation checks
npm run test:e2eRun each template's native tests through its script. The script composes the current src/main.psy with test cases and applies only the substitutions required by dargo's single-user mock runtime:
# PSY-20 Token Unit Tests
(cd token && npm test)
# PSY-721 NFT Unit Tests
(cd nft && npm test)