Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,16 @@
## Unreleased
### Added
- Units 11–20: canonical schemas, mechanism index generator, consumers mapping, WG bulk pack, repo templates, and verification scripts.
- m010 reference implementation vector verifier (`scripts/verify-m010-reference-impl.mjs`) with challenge replay coverage.
- m010 dataset integrity verifier (`scripts/verify-m010-datasets.mjs`) covering challenge linkage, lifecycle consistency, and expected output coherence.
- Additional m010 challenge fixtures for escalated and edge-timing scenarios, plus an intentionally invalid fixture for negative verification coverage.
- Additional verifier invariants for m010 (status/outcome consistency, duplicate detection, evidence minimums, and derived KPI coherence checks).

### Changed
- m010 scoring now excludes non-contributing signal states when `status` is present (`active`/`resolved_valid` only contribute).
- m010 KPI computation now emits `challenge_kpis` when challenge data is provided.
- m010 replay dataset/schema alignment expanded to cover challenge fixtures and lifecycle statuses (including `escalated`).
- m010 schemas are stricter on IDs/category formatting, evidence arrays, and challenge lifecycle guards (`status` ↔ `resolution`/`outcome` consistency).

### Notes
- This repo is primarily specification content; changes are intended to be deterministic and offline-friendly.
8 changes: 8 additions & 0 deletions docs/DEPENDENCIES.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,3 +22,11 @@ This repo is a coordination + specification registry for “agentic tokenomics

- High-level dependency notes: `docs/DEPENDENCIES.md` (this file)
- Mechanism-specific dependency notes: `mechanisms/<id>/README.md` → “External inputs”

## Downstream coordination for schema/output changes

When changes may affect consumers in other repos (for example `regen-heartbeat`), include in the PR:
- exact output key contract (added/changed/removed keys)
- whether change is `non-breaking` or `breaking`
- at least one deterministic fixture/vector update proving the new behavior
- rollback note (what to revert if downstream parsing fails)
21 changes: 21 additions & 0 deletions docs/MECHANISM_CONSUMERS.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,12 +9,33 @@ This document maps **mechanism IDs** to known **consumers** (agents, digests, sc
**Outputs**
- KPI JSON block schema: `mechanisms/m010-reputation-signal/schemas/m010_kpi.schema.json`
- Signal item schema: `mechanisms/m010-reputation-signal/schemas/m010_signal.schema.json`
- Challenge event schema: `mechanisms/m010-reputation-signal/schemas/m010_challenge.schema.json`

**Datasets (deterministic)**
- Replay fixtures: `mechanisms/m010-reputation-signal/datasets/fixtures/v0_sample.json`
- Challenge replay fixture: `mechanisms/m010-reputation-signal/datasets/fixtures/v0_challenge_sample.json`
- Escalated challenge fixture: `mechanisms/m010-reputation-signal/datasets/fixtures/v0_challenge_escalated_sample.json`
- Edge-timing challenge fixture: `mechanisms/m010-reputation-signal/datasets/fixtures/v0_challenge_edge_timing_sample.json`

**Known consumers**
- Heartbeat character: `signal-agent` (regen-heartbeat)
- Heartbeat replay runner: `scripts/replay-m010.mjs` (regen-heartbeat)
- Heartbeat stub runner: `scripts/stub-run-signal-agent.mjs` (regen-heartbeat)
- Heartbeat validator: `scripts/validate-signal-agent.mjs` (regen-heartbeat)

**Consumer contract (current)**
- Score output key: `score.reputation_score_0_1` (normalized `0..1` in v0 advisory).
- Contributing signal statuses: `active`, `resolved_valid`.
- Excluded signal statuses: `submitted`, `challenged`, `escalated`, `resolved_invalid`, `withdrawn`, `invalidated`.
- KPI denominator convention: `challenge_rate = challenges_filed / signals_emitted`.

**Compatibility policy**
- Non-breaking:
- adding optional fields
- adding new deterministic fixtures or vectors
- tightening documentation without changing output keys
- Potentially breaking (coordinate downstream first):
- renaming/removing output keys
- changing score range/key semantics
- changing KPI denominator semantics
- changing lifecycle contribution rules
18 changes: 17 additions & 1 deletion mechanisms/m010-reputation-signal/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
m010 defines a reputation / legitimacy signal for Regen ecosystem subjects (e.g., credit classes, projects, verifiers, methodologies, addresses) based on **stake-weighted endorsements** with **time decay**.

## What it outputs
- A normalized **reputation score** (0–1000) per `(subject_type, subject_id, category)`.
- A normalized **reputation score** (`reputation_score_0_1`, range `0–1`) per `(subject_type, subject_id, category)` in v0 advisory mode.
- A queryable history of submitted signals (endorsements), including state transitions (submitted, active, challenged, resolved_valid, resolved_invalid, withdrawn, invalidated).
- Challenge workflow events with evidence, resolution, and rationale.

Expand All @@ -27,3 +27,19 @@ Canonical JSON schemas for m010 outputs live in `schemas/`.
- `m010_signal.schema.json` — signal items with `status` lifecycle field
- `m010_challenge.schema.json` — challenge events with evidence and resolution
- `m010_kpi.schema.json` — KPI output including optional `challenge_kpis`

## Reference implementation checks
- Deterministic vectors are validated by `scripts/verify-m010-reference-impl.mjs`
- `challenge_rate` is computed as `challenges_filed / signals_emitted` for replay-period KPI reporting

## Consumer compatibility notes
- v0 score contract: consumers should read `score.reputation_score_0_1` (`0..1`).
- Status contribution contract: only `active` and `resolved_valid` contribute to score.
- Challenge KPI contract: when `challenges[]` are present, `challenge_kpis` includes:
- `challenges_filed`
- `challenge_rate`
- `avg_resolution_time_hours`
- `challenge_success_rate`
- `admin_resolution_timeout_rate`

Breaking changes for downstream consumers include renaming/removing these keys, changing denominator semantics, or changing lifecycle contribution rules.
2 changes: 1 addition & 1 deletion mechanisms/m010-reputation-signal/SPEC.md
Original file line number Diff line number Diff line change
Expand Up @@ -305,7 +305,7 @@ The following metrics should be tracked and published in periodic digests:
| KPI | Formula | Target |
|-----|---------|--------|
| `challenges_filed` | count of challenges per period | Informational |
| `challenge_rate` | challenges / total active signals | < 5% (healthy ecosystem) |
| `challenge_rate` | challenges / signals emitted in period | < 5% (healthy ecosystem) |
| `avg_resolution_time_hours` | mean(resolution_timestamp - challenge_timestamp) | < 168h (7 days) |
| `challenge_success_rate` | resolved_invalid / (resolved_valid + resolved_invalid) | Informational |
| `admin_resolution_timeout_rate` | auto_escalated / total_challenges | < 5% |
Expand Down
14 changes: 13 additions & 1 deletion mechanisms/m010-reputation-signal/datasets/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,10 @@ These fixtures are **deterministic inputs** for generating non-zero m010 KPI out
- `schema.json` — JSON schema for replay datasets
- `fixtures/v0_sample.json` — sample events used by Heartbeat replay runner (all signals active)
- `fixtures/v0_challenge_sample.json` — sample events exercising the challenge workflow (signals with varied statuses + challenge events with resolutions)
- `fixtures/v0_challenge_escalated_sample.json` — challenge replay including `escalated` status and timeout KPI behavior
- `fixtures/v0_challenge_edge_timing_sample.json` — challenge replay covering boundary timing (including zero-hour resolution)
- `fixtures/v0_challenge_invalid_resolution_sample.json` — intentionally invalid fixture for negative verification coverage
- `fixtures/v0_challenge_invalid_outcome_sample.json` — intentionally invalid fixture with status/outcome mismatch for negative verification coverage

## How they are used
A replay runner (e.g., in `regen-heartbeat`) can read a fixture file and compute:
Expand All @@ -16,7 +20,15 @@ A replay runner (e.g., in `regen-heartbeat`) can read a fixture file and compute

The challenge fixture (`v0_challenge_sample.json`) additionally exercises:
- Status-aware scoring: only `active` and `resolved_valid` signals contribute to score
- Challenge KPIs: `challenges_filed`, `challenge_rate`, `challenge_success_rate`, `avg_resolution_time_hours`
- Challenge KPIs: `challenges_filed`, `challenge_rate` (`challenges_filed / signals_emitted`), `challenge_success_rate`, `avg_resolution_time_hours`
- The `expected_outputs` field documents which signals should be included/excluded

These datasets are **advisory-only** and do not imply enforcement or on-chain actions.

## Integrity checks
Dataset integrity is validated by `scripts/verify-m010-datasets.mjs`, including:
- challenge-to-signal linkage (`challenge.signal_id` must reference an existing signal)
- category consistency between challenge and targeted signal
- resolution timestamp ordering and resolution presence rules by challenge status
- consistency of `expected_outputs.contributing_signals` / `excluded_signals` with status-based contribution rules
- negative checks that intentionally invalid fixtures fail with the expected validation reason
Original file line number Diff line number Diff line change
@@ -0,0 +1,144 @@
{
"mechanism_id": "m010",
"scope": "v0_advisory_challenge_edge_timing_replay",
"as_of": "2026-02-15T12:00:00Z",
"description": "Fixture exercising zero/low resolution durations and fresh events at as_of boundary.",
"events": [
{
"signal_id": "signal-edge-1",
"timestamp": "2026-02-15T11:00:00Z",
"subject_type": "Project",
"subject_id": "P-regen-200",
"category": "delivery_risk",
"endorsement_level": 3,
"signaler_id": "signaler_edge_a",
"status": "active",
"evidence": {
"koi_links": ["koi://note/edge-1"],
"ledger_refs": ["ledger://tx/4001"]
}
},
{
"signal_id": "signal-edge-2",
"timestamp": "2026-02-15T12:00:00Z",
"subject_type": "CreditClass",
"subject_id": "C01-020",
"category": "registry_quality",
"endorsement_level": 4,
"signaler_id": "signaler_edge_b",
"status": "resolved_valid",
"evidence": {
"koi_links": ["koi://note/edge-2"],
"ledger_refs": ["ledger://tx/4002"]
}
},
{
"signal_id": "signal-edge-3",
"timestamp": "2026-02-14T12:00:00Z",
"subject_type": "Verifier",
"subject_id": "V-EdgeMRV",
"category": "attestation_quality",
"endorsement_level": 5,
"signaler_id": "signaler_edge_c",
"status": "resolved_invalid",
"evidence": {
"koi_links": ["koi://note/edge-3"],
"ledger_refs": ["ledger://tx/4003"]
}
},
{
"signal_id": "signal-edge-4",
"timestamp": "2026-02-13T12:00:00Z",
"subject_type": "Address",
"subject_id": "regen1edge...0004",
"category": "operator_trust",
"endorsement_level": 2,
"signaler_id": "signaler_edge_d",
"status": "withdrawn",
"evidence": {
"koi_links": ["koi://note/edge-4"],
"ledger_refs": ["ledger://tx/4004"]
}
}
],
"challenges": [
{
"challenge_id": "ch-edge-001",
"signal_id": "signal-edge-2",
"challenger_id": "challenger_edge_a",
"category": "registry_quality",
"rationale": "This challenge was immediately resolved at submission time to validate zero-hour resolution handling in deterministic KPI computation.",
"severity": "LOW",
"requested_outcome": "FLAG_FOR_REVIEW",
"evidence": {
"koi_links": ["koi://note/ch-edge-1"],
"ledger_refs": ["ledger://tx/ch-edge-1"],
"web_links": []
},
"timestamp": "2026-02-15T12:00:00Z",
"status": "resolved_valid",
"resolution": {
"resolved_by": "admin_edge",
"resolved_at": "2026-02-15T12:00:00Z",
"outcome": "VALID",
"rationale": "Instant resolution for deterministic boundary test."
}
},
{
"challenge_id": "ch-edge-002",
"signal_id": "signal-edge-3",
"challenger_id": "challenger_edge_b",
"category": "attestation_quality",
"rationale": "Evidence review completed within thirty minutes and determined the underlying verifier claim was invalid for this reporting period.",
"severity": "HIGH",
"requested_outcome": "INVALIDATE",
"evidence": {
"koi_links": ["koi://note/ch-edge-2"],
"ledger_refs": ["ledger://tx/ch-edge-2"],
"web_links": []
},
"timestamp": "2026-02-14T11:30:00Z",
"status": "resolved_invalid",
"resolution": {
"resolved_by": "admin_edge",
"resolved_at": "2026-02-14T12:00:00Z",
"outcome": "INVALID",
"rationale": "Short-window review confirmed evidence inconsistency."
}
},
{
"challenge_id": "ch-edge-003",
"signal_id": "signal-edge-4",
"challenger_id": "challenger_edge_c",
"category": "operator_trust",
"rationale": "Pending challenge remains open for withdrawn signal to verify unresolved challenge handling and exclusion behavior across score and KPI outputs.",
"severity": "MEDIUM",
"requested_outcome": "FLAG_FOR_REVIEW",
"evidence": {
"koi_links": ["koi://note/ch-edge-3"],
"ledger_refs": ["ledger://tx/ch-edge-3"],
"web_links": []
},
"timestamp": "2026-02-14T10:00:00Z",
"status": "pending"
}
],
"expected_outputs": {
"description": "Edge timing fixture with zero-hour resolution and at-as_of signal timestamps.",
"contributing_signals": [
"signal-edge-1 (active, endorsement=3)",
"signal-edge-2 (resolved_valid, endorsement=4)"
],
"excluded_signals": [
"signal-edge-3 (resolved_invalid)",
"signal-edge-4 (withdrawn)"
],
"challenge_kpis": {
"challenges_filed": 3,
"challenge_rate": 0.75,
"challenge_success_rate": 0.5,
"avg_resolution_time_hours": 0.25,
"admin_resolution_timeout_rate": 0
}
}
}
Loading