2. Claim Schemas and the Subject Type System
2.1 Claim Schema
A Claim is the atomic input to the Verification Engine. Every verification corresponds to exactly one claim evaluation under one context.
{
"claimId": "string // Content-addressed identifier (Keccak-256)",
"schemaVersion": "string // Semantic version (e.g., '1.0.0')",
"predicate": "PredicateId // The property being evaluated",
"statement": "string // Human-readable statement of the claim",
"subject": "Subject // The entity the claim refers to",
"context": "Context // Where and when the claim applies",
"scope": "Scope // Constraints on evidence graph expansion"
}
Validation Rules:
claimIdMUST be the Keccak-256 hash of the canonically encoded claim (excludingclaimIditself)schemaVersionMUST follow semantic versioning (MAJOR.MINOR.PATCH)predicateMUST reference a registered predicate in the Predicate Registry (Section 2.4)subject.typeMUST be compatible with the predicate's admissible subject typescontextblock ranges MUST be non-empty and MUST reference finalized blocks- An incompletely specified claim is non-verifiable by design
2.2 Subject Type System
A Subject is the entity a claim refers to. Subjects are typed so that only valid predicates and evidence sources apply.
SubjectType = TOKEN | ACCOUNT | CONTRACT | POOL | TX | COHORT
{
"subjectId": "string // Unique identifier within the claim",
"type": "SubjectType",
"chain": "ChainType // 'solana' | 'ethereum' | 'base' | ...",
"ref": {
"mint": "string | null // Token mint address (TOKEN)",
"programId": "string | null // Program/contract address (CONTRACT)",
"poolAddress": "string | null // Liquidity pool address (POOL)",
"txHash": "string | null // Transaction hash (TX)",
"accountAddress": "string | null // Wallet address (ACCOUNT)"
},
"displayName": "string // Human-readable label"
}
Observed vs. Inferred Subjects:
- An observed subject is directly addressable on-chain (a token mint, an account).
- An inferred subject is produced by a versioned inference method (e.g., a wallet cluster, a cohort of coordinated actors). Inferred subjects MUST carry:
{
"inferenceMethod": "string // Method that produced this subject",
"methodVersion": "string // Version of that method",
"confidence": "number // 0-100"
}
Identity assertions are NOT assumed. Asserting that two accounts belong to the same entity is itself a claim that must be evaluated.
2.3 Context and Scope
{
"Context": {
"chain": "ChainType",
"blockFrom": "number // Inclusive start block/slot",
"blockTo": "number // Inclusive end block/slot",
"timeFrom": "string // ISO 8601 timestamp of blockFrom",
"timeTo": "string // ISO 8601 timestamp of blockTo"
},
"Scope": {
"maxHops": "number | null // Maximum graph expansion depth",
"maxNodes": "number | null // Maximum evidence graph node count",
"maxEdges": "number | null // Maximum evidence graph edge count",
"temporalLookback": "number | null // Maximum blocks to look back from blockFrom",
"evidenceAllowlist": "string[] | null // Permitted evidence source types",
"notes": "string | null // Free-text scope annotations"
}
}
Scope serves as a constraint against ambiguity and unbounded aggregation. Two evaluations of the same predicate over different scopes are treated as distinct claim evaluations.
2.4 Predicate Registry
The Predicate Registry defines the set of evaluable properties. Each predicate specifies its evaluation class, admissible subject types, required evidence sources, and applicable inference methods. Predicates are versioned independently from the engine (see Section 2.5 for versioning rules).
{
"predicateId": "string // Stable identifier (e.g., 'supply_concentration')",
"version": "string // Semantic version of this predicate definition",
"name": "string",
"evaluationClass": "DETERMINISTIC | INFERENTIAL",
"admissibleSubjects": "SubjectType[]",
"requiredEvidence": "EvidenceSourceType[]",
"methods": "MethodReference[]",
"description": "string",
"status": "ACTIVE | DEPRECATED | RETIRED"
}
Initial Predicate Set (Memecoin Intel Portal):
| Predicate ID | Version | Eval Class | Subject Types | Description |
|---|---|---|---|---|
supply_concentration |
1.0.0 | DETERMINISTIC | TOKEN | Top-N holder % of circulating supply |
wallet_clustering |
1.0.0 | INFERENTIAL | TOKEN | Coordinated wallet group detection |
liquidity_depth |
1.0.0 | DETERMINISTIC | POOL | Price impact for given sell amount |
liquidity_health |
1.0.0 | DETERMINISTIC | TOKEN, POOL | TVL / market cap ratio and stability |
sniper_dominance |
1.0.0 | INFERENTIAL | TOKEN | % of supply held by detected snipers |
wash_trading_ratio |
1.0.0 | INFERENTIAL | TOKEN, POOL | Artificial volume estimation |
holder_distribution |
1.0.0 | DETERMINISTIC | TOKEN | Gini, HHI, Nakamoto coefficients |
holder_growth_trend |
1.0.0 | DETERMINISTIC | TOKEN | Rate of change in unique holder count |
buy_sell_pressure |
1.0.0 | DETERMINISTIC | TOKEN | Buy/sell ratio and volume balance |
contract_security |
1.0.0 | DETERMINISTIC | CONTRACT | Mint authority, freeze, upgrade status |
lp_lock_status |
1.0.0 | DETERMINISTIC | POOL | LP token lock/burn verification |
price_action_pattern |
1.0.0 | INFERENTIAL | TOKEN | Lifecycle phase detection |
manipulation_signals |
1.0.0 | INFERENTIAL | TOKEN | Overextended pump, coordinated activity |
social_presence |
1.0.0 | DETERMINISTIC | TOKEN | Existence of Twitter, TG, Discord |
kol_mention_quality |
1.0.0 | INFERENTIAL | TOKEN | KOL impact scoring and timing |
community_health |
1.0.0 | INFERENTIAL | TOKEN | Organic engagement assessment |
narrative_strength |
1.0.0 | INFERENTIAL | TOKEN | Memetic propagation and uniqueness |
2.5 Predicate Versioning
Predicates are versioned independently from the engine to distinguish between changes in what is being measured (predicate semantics) and changes in how the system operates (engine infrastructure).
Predicate Semantic Version: MAJOR.MINOR.PATCH
| Level | What Changes | Effect on Historical VOs | Example |
|---|---|---|---|
| MAJOR | The predicate measures something fundamentally different: new formula, different result semantics, changed threshold interpretation | Historical VOs remain valid under their recorded predicate version. New evaluations use the new version. VOs under different MAJOR versions are not comparable. | supply_concentration changes from "top-10 holders" to "Gini coefficient" |
| MINOR | Expanded capability that doesn't change existing behavior: new optional parameters, additional output fields, new admissible subject types | Historical VOs remain valid. New evaluations MAY use new features. VOs under different MINOR versions are comparable for the shared feature set. | supply_concentration adds an optional topN parameter (default remains 10) |
| PATCH | Documentation clarification, description updates, no behavioral change | No effect. | Predicate description improved |
Predicate-Engine Binding:
Each engine version includes a Predicate Manifest — a frozen snapshot of which predicate versions it supports:
{
"engineVersion": "1.2.0",
"predicateManifest": [
{ "predicateId": "supply_concentration", "version": "1.0.0" },
{ "predicateId": "wallet_clustering", "version": "1.1.0" },
{ "predicateId": "liquidity_depth", "version": "2.0.0" }
]
}
Binding Rules:
Frozen within engine version: A given engine version ALWAYS uses the same predicate versions. Engine
1.2.0always evaluatessupply_concentrationat predicate version1.0.0. This is essential for replay determinism — a validator replaying a VO under engine1.2.0knows exactly which predicate semantics apply.Engine MINOR bump for predicate changes: Adding a new predicate version to the manifest requires at minimum an engine MINOR version bump. This ensures the mapping from engine version to predicate behavior is unambiguous.
Engine MAJOR bump for breaking predicate changes: If a predicate MAJOR version is introduced (e.g.,
supply_concentration2.0.0), the engine MUST bump its own MAJOR version, because the samepredicateIdnow means something different and historical comparisons across the boundary are invalid.Predicate deprecation: A predicate version can be deprecated (new evaluations discouraged) independently of the engine. However, it remains replayable as long as any engine version that references it is in CURRENT or SUPPORTED state (Section 5.5). A predicate reaches RETIRED status only when all engine versions that include it are RETIRED.
Claim Resolution:
When a claim references predicate: "supply_concentration" without an explicit version:
- The engine resolves to the predicate version specified in its own Predicate Manifest
- The resolved version is recorded in the VO's
methodsarray (see Section 6.1) - Callers MAY explicitly request a predicate version via the API; the engine MUST reject the request if the requested version is not in its manifest