You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Specification of the Polymesh blockchain runtime logic, written for engineers and AI agents
reviewing or modifying this codebase. Each document describes one subsystem: its data model,
extrinsics with their authorization requirements, core flows, cross-pallet interactions, and the
invariants a reviewer should check when the code changes.
Conventions
Code citations use path:line (symbol_name). Line numbers drift as code changes; the symbol
name is authoritative — re-locate with rg if a line number is stale.
"GC" = Governance Council (root or committee origins). "DID" = identity (IdentityId).
"Primary key" / "secondary key" refer to the account keys attached to a DID.
Extrinsic tables list the effective authorization: what origin must be and which
permission checks are applied after origin resolution.
POLYX is the native token (6 decimals; ONE_POLY = 1_000_000).
Repository architecture
Node (src/): standard Substrate node (BABE/GRANDPA consensus, BEEFY/MMR).
Binary entry src/bin/main.rs; service wiring src/service.rs; chain specs src/chain_spec/.
Three runtimes (pallets/runtime/{develop,testnet,mainnet}): share one identical
spec_version (checked by scripts/check_spec_and_cargo_version.sh). Most configuration and
the runtime macro scaffolding live in pallets/runtime/common/src/runtime.rs (macro
misc_pallet_impls! / common types) with per-chain constants in each runtime's
constants.rs/runtime.rs. Runtime changes usually must be wired in all three.
Forked polkadot-sdk: all sp-*/sc-*/frame-*/pallet-staking/pallet-revive deps come
from PolymeshAssociation/polkadot-sdk (branch pinned in root Cargo.toml[workspace.dependencies]). The fork mainly exists to support Polymesh's identity/permission
system (e.g. fee-payer redirection hooks, revive origin handling).
Shared tests: pallets/runtime/tests/ (polymesh-runtime-tests, ExtBuilder-based mock
runtime). integration/ is a separate workspace driving a live chain over RPC.
Weights: central in pallets/weights/src/*.rs, not inside pallets.
Runtime differences
Pallet
develop
testnet
mainnet
Sudo
yes
yes (sudo key)
no
ConfidentialAssets (index 70)
yes
yes
no
Revive (index 80)
yes
yes
yes
Everything else is identical modulo constants (e.g. settlement lock periods, CA defaults).
Identity-first: almost every extrinsic resolves the caller's account key to a DID before
doing anything. Accounts are cheap; identities carry claims, portfolios, asset roles.
One account key belongs to at most one DID (or one multisig).
Layered permissions: a call passes up to four gates —
(a) key→DID resolution + DID-not-frozen,
(b) secondary-key extrinsic permission (pallet/function subsets, recorded per-call by the
StoreCallMetadata transaction extension),
(c) secondary-key asset / portfolio subsets checked by the target pallet,
(d) asset-scoped agent group permission (external-agents) for asset admin calls.
Primary keys skip (b)/(c) but not (d).
Transfers are settlement-centric: every asset movement (including the direct
Asset::transfer_asset UX and ERC-20-style allowance spends) funnels into the settlement
engine's instruction machinery, which enforces custody, affirmations, compliance, statistics,
and venue filtering. Same-DID portfolio moves skip compliance/statistics.
Authorizations: privileged relationship changes (join identity, rotate primary key, become
agent, transfer ticker/portfolio custody...) are two-phase: issuer creates an Authorization,
target accepts it. The issuer pays the acceptance fees (see doc 14).