{"name":"Agentic Finance Graph — data quality","description":"Assertion checks over the tables every public number is computed from. Zero failing rows means pass. block = published numbers would be wrong while it fails; warn = late or drifting; info = worth knowing, not a defect.","license":"https://creativecommons.org/licenses/by/4.0/","as_of":"2026-11-10T23:22:26.577Z","run_id":"dq-202611102317","producer":"AFG-Pulse data-quality suite (assertion checks over our own tables)","summary":{"checks":56,"passing":52,"block_failing":0,"warn_failing":2,"info_flagged":2,"errors":0,"health_score":0.9817},"parameters":{"max_single_payment_usd":5000000,"pass_backlog_hours":24,"money_fresh_hours":48,"volume_ratio":4,"shared_wallet_min":3,"fee_split_tolerance":0.02,"acp_paid_tolerance":1.01,"cursor_stall_cycles":4,"full_pass_hours":48,"sample":5},"health_formula":"weighted pass rate over block and warn checks; weight = dataset weight (rank tables 3, published snapshots 2, partner tables 1) x severity (block 2, warn 1); info checks never move the score; an error counts as a failure","checks":[{"id":"chain_lag","table":"partner_cursors","dimension":"timeliness","severity":"warn","weight":1,"baseline":false,"what":"An other-chain registry watcher (Ethereum, Arbitrum, OP Mainnet, Polygon) is more than an hour of blocks behind the chain head, or has blocks it skipped and never scanned. Its mint and owner figures are partial until both are zero. Added 12 Oct 2026, when Arbitrum was about 113,000 blocks behind with a 1.2 million-block gap while health read 1.00.","status":"pass","failing":0,"ms":12},{"id":"sweep_lag","table":"partner_cursors","dimension":"timeliness","severity":"warn","weight":2,"baseline":false,"what":"The sweep's live pass, which flags every bound wallet that moved a stablecoin for the payment scan, has not advanced in six hours. Payments made since then are not being read. Added 23 Oct 2026.","status":"pass","failing":0,"ms":2},{"id":"census_gap","table":"registrations","dimension":"completeness","severity":"warn","weight":2,"baseline":false,"what":"More than 100 Base registrations older than 36 hours have no actor yet, so they cannot be bound or ranked. The census runs daily; burned tokens account for a few dozen permanent gaps. Added 23 Oct 2026.","status":"pass","failing":0,"ms":2543},{"id":"payer_queue_age","table":"wallets","dimension":"timeliness","severity":"warn","weight":1,"baseline":false,"what":"Bound wallets the sweep saw move a stablecoin have waited more than three days for their first read by the payment scan. Their payments are missing from every count until then. Added 23 Oct 2026.","status":"pass","failing":0,"ms":41},{"id":"payer_vs_logs","table":"logreader_compare","dimension":"completeness","severity":"warn","weight":2,"baseline":false,"what":"Payments measured two ways disagree: for a one-in-five sample of bound wallets, the stablecoin Transfer logs read straight from the chain (afg-logreader) hold more than 10% transfers that the payment reader has not stored, for a window that closed 24 hours earlier. It showed 52,933 of 52,968 on 23 Oct 2026 (the starved payment queue) and had shown a gap since 22 Oct 03:41 UTC without any alarm. Added 23 Oct 2026.","status":"pass","failing":0,"ms":7},{"id":"offsite_backup_stale","table":"partner_cursors","dimension":"timeliness","severity":"warn","weight":2,"baseline":false,"what":"The nightly database dump has not been copied to the off-site Storage Box and verified there for more than 36 hours (afg-offsite, daily at 04:10 UTC; the copy is checked with the box's own sha256sum). Until 24 Oct 2026 every backup lived on the same disk as the database. Added 24 Oct 2026.","status":"pass","failing":0,"ms":1},{"id":"ops_job_failing","table":"ops_job_health","dimension":"timeliness","severity":"warn","weight":2,"baseline":false,"what":"A collector job is failing right now. afg-guard reads every afg-* job every 10 minutes, retries a failed timer job once and alerts the founder on a second failure in a row; until the job runs clean its figures stop refreshing. The cause is read from the job's own log.","status":"pass","failing":0,"ms":3},{"id":"ops_job_near_limit","table":"ops_job_health","dimension":"timeliness","severity":"warn","weight":1,"baseline":false,"what":"A collector job used 85% or more of its memory limit (the service cap or Node's own heap ceiling, whichever is lower) or of its time limit on its last run. It will fail as the data grows unless it is made lighter or given more room; on 27-28 Oct nine jobs failed this way with no warning.","status":"pass","failing":0,"ms":1},{"id":"ops_guard_silent","table":"ops_job_health","dimension":"timeliness","severity":"warn","weight":2,"baseline":false,"what":"afg-guard has not checked the collector jobs for more than 30 minutes, so failures and limits are not being watched.","status":"pass","failing":0,"ms":1},{"id":"ops_disk_low","table":"ops_system","dimension":"timeliness","severity":"warn","weight":2,"baseline":false,"what":"Less than 10 GB free on the collector's disk (on 26 Oct one query filled it and five jobs died). Archives belong on the off-site Storage Box.","status":"pass","failing":0,"ms":2},{"id":"offsite_box_filling","table":"partner_cursors","dimension":"timeliness","severity":"warn","weight":1,"baseline":false,"what":"The off-site Storage Box (1 TB) is 75% full or more. Nightly dumps are kept 60 days there and grow with the ledger; snapshots, editions, daily site archives, sum-log heads and code are kept forever. Time to plan retention or a larger box before a copy fails.","status":"pass","failing":0,"ms":1},{"id":"unexplained_step","table":"series_steps","dimension":"consistency","severity":"warn","weight":1,"baseline":false,"what":"One of our own archived series stepped in the last 14 days (a material move concentrated in one day that persisted) and neither a dated change of ours in /api/changepoints nor a checked note explains it. Either we changed something without registering it, or the world moved and the move needs a dated note. Found by afg-steps: PELT (Killick, Fearnhead & Eckley 2012) over each daily series, confirmed by a one-day jump test; the list is at /api/steps. Added 12 Oct 2026.","status":"fail","failing":2,"ms":8,"sample":[{"metric":"poison_copy_lag_median_min","step_day":"2026-11-07","before":"275.1667","after":"551.6667","z":"46.3"},{"metric":"heartbeat_bursty_share","step_day":"2026-11-06","before":"0.2764","after":"0.3101","z":"8.4"}]},{"id":"me_required_fields","table":"money_events","dimension":"completeness","severity":"block","weight":3,"baseline":false,"what":"A payment row is missing a field every downstream figure needs.","status":"pass","failing":0,"ms":4914},{"id":"me_duplicate_log","table":"money_events","dimension":"uniqueness","severity":"block","weight":3,"baseline":false,"what":"The same on-chain log (transaction + log position) is stored twice, which double-counts it.","status":"pass","failing":0,"ms":44863},{"id":"me_identical_in_one_tx","table":"money_events","dimension":"uniqueness","severity":"info","weight":1,"baseline":false,"what":"Identical transfers inside one transaction. Usually a batch payment, not a duplicate: on 2026-09-24 all four counted groups were checked against their on-chain receipts and every one matched. Rows without a log position cannot be told apart from a double insert, which is why me_duplicate_log exists.","status":"fail","failing":15454,"ms":49752,"sample":[{"tx":"0x0000eafd46471b7662c9e7003fd88352b3034d448b0a2b9588e439dcef6f4e8c","from_caip10":"eip155:8453:0xbe061d84c50e156e2faa791228662e3b52c906e2","to_id":"eip155:8453:0x76d4a669c8937a871ca0022d9f5c42c1d4afe9a7","amount_usd":"0.010000","copies":2},{"tx":"0x0000eafd46471b7662c9e7003fd88352b3034d448b0a2b9588e439dcef6f4e8c","from_caip10":"eip155:8453:0xbe061d84c50e156e2faa791228662e3b52c906e2","to_id":"eip155:8453:0xb7dace47c583ffb2d76ff26afe89d582b2182276","amount_usd":"0.001000","copies":7},{"tx":"0x000d918e16502bfa782f8a85709d03da3612a0ec7357b44f53a670d1694fb9a2","from_caip10":"eip155:8453:0xc9d53f2a9a2bb83b933b630480e4dbe1ce7e0c92","to_id":"eip155:8453:0xc8be97914211c3d3bc618bcfd3b6dccaa161b5dc","amount_usd":"0.001000","copies":3},{"tx":"0x000f6ae37c2c1772c0ba3e584d936f64c980f569c180af100bb96c9930ab0d2d","from_caip10":"eip155:8453:0xbe82db7df8cab673ad884e0d480b9821506cd280","to_id":"eip155:8453:0x90ef8e32985d70a10e98c19334fda93ea28b5ce1","amount_usd":"0.100000","copies":19},{"tx":"0x000f6ae37c2c1772c0ba3e584d936f64c980f569c180af100bb96c9930ab0d2d","from_caip10":"eip155:8453:0xbe82db7df8cab673ad884e0d480b9821506cd280","to_id":"eip155:8453:0xb7dace47c583ffb2d76ff26afe89d582b2182276","amount_usd":"0.010000","copies":19}]},{"id":"me_counted_without_log_index","table":"money_events","dimension":"uniqueness","severity":"warn","weight":2,"baseline":false,"what":"Counted payments stored before log positions were recorded. me_duplicate_log cannot see them, so a double insert among them would reach the headline. Added 9 Oct 2026 (charter audit); the backfill re-reads their receipts.","status":"pass","failing":0,"ms":5170},{"id":"registry_count_vs_daily","table":"snapshots","dimension":"consistency","severity":"warn","weight":2,"baseline":false,"what":"The cited all-chain registration total (agenteconomy.to) did not move while the same source's all-chain daily series reported new mints: one of the two is stale. Seen 30 Sep to 3 Oct 2026; added 9 Oct (charter audit) so a registration rate is never published from a stale total. Until 9 Oct 2026 15:30 UTC this compared the Base-only total with the all-chain daily series and fired falsely.","status":"pass","failing":0,"ms":13},{"id":"base_registrations_two_ways","table":"registrations","dimension":"consistency","severity":"warn","weight":3,"baseline":false,"what":"Base registrations measured two ways: our dated registrations table counted at the exact end of a UTC day differs from The Graph's Agent0 subgraph total for that day. Added 12 Oct 2026, when 9, 10 and 11 Oct agreed to the registration; a gap means one of the two indexers missed or double-counted a mint.","status":"pass","failing":0,"ms":4},{"id":"base_registrations_cited_vs_own","table":"snapshots","dimension":"consistency","severity":"info","weight":2,"baseline":false,"what":"The Base registration total cited from agenteconomy.to and our own count from the Identity Registry contract differ by more than 1%. Informational: the cited figure is labelled as cited and the headline uses our own count (registrations_minted_total). On 9 Oct 2026 the cited total was 100,119 while the chain's newest agent id at 11:00 UTC was 99,013 (99,014 registrations), read both from public RPC and from our live mint feed. Added 9 Oct 2026.","status":"pass","failing":0,"ms":3},{"id":"me_missing_log_index","table":"money_events","dimension":"completeness","severity":"info","weight":1,"baseline":false,"what":"Payments stored before log positions were recorded. They fill in as the payment scan re-reads each wallet; until then me_duplicate_log cannot see them.","status":"pass","failing":0,"ms":5831},{"id":"me_amount_range","table":"money_events","dimension":"validity","severity":"block","weight":3,"baseline":false,"what":"A payment amount is negative or implausibly large for a single agent transfer.","status":"pass","failing":0,"ms":8350},{"id":"me_known_values","table":"money_events","dimension":"validity","severity":"block","weight":3,"baseline":false,"what":"A kind, rail, asset or confidence value appeared that no downstream code knows how to treat. Since 27 Sep 2026: PAY and EARN (income), four stablecoins.","status":"pass","failing":0,"ms":6136},{"id":"me_address_format","table":"money_events","dimension":"validity","severity":"block","weight":3,"baseline":false,"what":"A sender or recipient is not a lowercase CAIP-10 address, so joins against it silently miss.","status":"pass","failing":0,"ms":71121},{"id":"me_counted_self_payment","table":"money_events","dimension":"consistency","severity":"block","weight":3,"baseline":false,"what":"A wallet paying itself is counted as spending. Moving your own money is not paying anybody.","status":"pass","failing":0,"ms":4812},{"id":"me_pre_registration_leak","table":"money_events","dimension":"consistency","severity":"block","weight":3,"baseline":false,"what":"A payment from BEFORE the agent was registered is counted. This exact leak once overstated the headline by 46%.","status":"pass","failing":0,"ms":7473},{"id":"me_orphan_actor","table":"money_events","dimension":"referential","severity":"block","weight":3,"baseline":false,"what":"A payment points at an actor that does not exist.","status":"pass","failing":0,"ms":10027},{"id":"me_sender_never_bound","table":"money_events","dimension":"referential","severity":"warn","weight":3,"baseline":false,"what":"A payment is attributed to an agent whose wallet was never bound to it, so the attribution has no basis.","status":"pass","failing":0,"ms":6368},{"id":"me_pass_through_backlog","table":"money_events","dimension":"freshness","severity":"warn","weight":3,"baseline":false,"what":"Counted payments older than the backlog window have not been checked for pass-through routing yet. Pre-registration payments are excluded from every total already, so they never need checking (the first run flagged 3,313 of them by mistake).","status":"pass","failing":0,"ms":3763},{"id":"me_freshness","table":"money_events","dimension":"freshness","severity":"warn","weight":3,"baseline":false,"what":"The newest observed payment is older than the scan's own cadence allows: the payment scan may have stalled.","status":"pass","failing":0,"ms":1},{"id":"me_volume_swing","table":"money_events","dimension":"volume","severity":"info","weight":1,"baseline":true,"what":"Yesterday's number of newly recorded payments is far from the trailing 7-day median. Needs a week of history.","status":"pass","failing":0,"ms":752},{"id":"actor_liveness_range","table":"actors","dimension":"validity","severity":"block","weight":3,"baseline":false,"what":"A liveness level outside the L0–L9 ladder.","status":"pass","failing":0,"ms":3},{"id":"actor_rank_without_evidence","table":"actors","dimension":"consistency","severity":"block","weight":3,"baseline":false,"what":"An agent is ranked L7 or above with no countable payment behind it. The rank is the product; this is the check that protects it.","status":"pass","failing":0,"ms":1891},{"id":"actor_evidence_without_rank","table":"actors","dimension":"consistency","severity":"warn","weight":3,"baseline":false,"what":"An agent has a payment that qualifies for L7 under ladder v2 (counted, not inferred, left its control) but is still ranked below L7: a promotion is pending until the next rank run (afg-payer, every 3 h).","status":"pass","failing":0,"ms":744},{"id":"actor_rank_evidence_withdrawn","table":"actors","dimension":"consistency","severity":"warn","weight":2,"baseline":false,"what":"An agent ranked L7+ no longer has a payment that left its control (a position, own-address or bridged-back finding arrived after the last rank run). The next rank run (afg-payer, every 3 h) takes it down; a warning, so the gate does not stall publishing for up to three hours.","status":"fail","failing":2,"ms":357,"sample":[{"actor_id":"act_8453_45815","liveness":7},{"actor_id":"act_8453_63828","liveness":7}]},{"id":"actor_unmeasured_l6","table":"actors","dimension":"consistency","severity":"block","weight":2,"baseline":false,"what":"An agent shows L6 without a probe that measured L6. Ladder v1 parked withdrawn ranks at L6; v2 never does.","status":"pass","failing":0,"ms":3061},{"id":"actor_l9_counterparties","table":"actors","dimension":"consistency","severity":"block","weight":3,"baseline":false,"what":"An L9 agent does not have even three distinct counterparties in 30 days, measured as of the last rank computation (afg-payer, every 3 h). Ladder v2 (13 Oct 2026) asks more (three independent ones among payments that left its control), so this is a necessary condition that a correct rank always passes. Until 9 Oct 2026 the window ended now, so a counterparty ageing out between two rank runs failed the check until the next run demoted the agent.","status":"pass","failing":0,"ms":3582},{"id":"binding_orphan_actor","table":"bindings","dimension":"referential","severity":"block","weight":3,"baseline":false,"what":"A binding points at an actor that does not exist.","status":"pass","failing":0,"ms":2250},{"id":"binding_wallet_format","table":"bindings","dimension":"validity","severity":"block","weight":3,"baseline":false,"what":"A bound wallet is not a lowercase CAIP-10 address.","status":"pass","failing":0,"ms":6005},{"id":"binding_interval","table":"bindings","dimension":"consistency","severity":"block","weight":3,"baseline":false,"what":"A binding closes before it opens.","status":"pass","failing":0,"ms":131},{"id":"binding_shared_wallet","table":"bindings","dimension":"uniqueness","severity":"info","weight":1,"baseline":false,"what":"One wallet is currently bound to several identities: an operator wallet, not an agent wallet.","status":"fail","failing":2445,"ms":464,"sample":[{"wallet":"eip155:8453:0x0008748e281e15ad766b1b6e253df3f4bb2b7a3c","identities":9},{"wallet":"eip155:8453:0x002cfcf168a3649c051be54009eb866c3aa3e402","identities":4},{"wallet":"eip155:8453:0x003ab2103ee5e1ebd97b496039b30a90b640ec5d","identities":7},{"wallet":"eip155:8453:0x0049dce82b33813f027c0933784b5a2541a19582","identities":60},{"wallet":"eip155:8453:0x0079b0baeb34975a16e21d599fa7e33918657fd4","identities":6}]},{"id":"snapshot_not_finite","table":"snapshots","dimension":"validity","severity":"block","weight":2,"baseline":false,"what":"A published value is null, NaN or infinite.","status":"pass","failing":0,"ms":4},{"id":"snapshot_from_future","table":"snapshots","dimension":"validity","severity":"block","weight":2,"baseline":false,"what":"A published value claims a timestamp in the future.","status":"pass","failing":0,"ms":1},{"id":"snapshot_rate_out_of_range","table":"snapshots","dimension":"validity","severity":"block","weight":2,"baseline":false,"what":"A published rate or share is below 0 or above 1. A negative share was once published live.","status":"pass","failing":0,"ms":2},{"id":"series_missing_definition","table":"series","dimension":"completeness","severity":"warn","weight":2,"baseline":false,"what":"A metric was written in the last day without a definition id, so /def cannot explain it.","status":"pass","failing":0,"ms":1090},{"id":"acp_negative_amount","table":"acp_jobs","dimension":"validity","severity":"block","weight":1,"baseline":false,"what":"An ACP job has a negative amount.","status":"pass","failing":0,"ms":13},{"id":"acp_paid_exceeds_funded","table":"acp_jobs","dimension":"consistency","severity":"warn","weight":1,"baseline":false,"what":"An ACP job paid out more than it was funded with (outside rounding).","status":"pass","failing":0,"ms":2},{"id":"bankr_address_format","table":"bankr_launches","dimension":"validity","severity":"block","weight":1,"baseline":false,"what":"A Bankr token, deployer or fee recipient is not a lowercase address.","status":"pass","failing":0,"ms":6646},{"id":"bankr_fee_split","table":"bankr_launches","dimension":"consistency","severity":"warn","weight":1,"baseline":false,"what":"Bankr's platform plus creator fee exceeds the total fee it reported for the same token.","status":"pass","failing":0,"ms":495},{"id":"bankr_negative_fee","table":"bankr_launches","dimension":"validity","severity":"block","weight":1,"baseline":false,"what":"A cited Bankr fee is negative.","status":"pass","failing":0,"ms":517},{"id":"partner_shared_flag","table":"partner_identities","dimension":"consistency","severity":"block","weight":1,"baseline":false,"what":"A wallet declared by several partner identities is not flagged as shared, so it could count as an agent wallet.","status":"pass","failing":0,"ms":327},{"id":"x402_address_format","table":"x402_recipients","dimension":"validity","severity":"block","weight":1,"baseline":false,"what":"A named x402 seller is not a lowercase address, so payments to it are never attributed.","status":"pass","failing":0,"ms":9},{"id":"cursor_stalled","table":"partner_cursors","dimension":"freshness","severity":"warn","weight":2,"baseline":false,"what":"A worker that pages through a source has not saved a new position for several of its own cycles, so whatever it feeds has quietly stopped updating.","status":"pass","failing":0,"ms":2},{"id":"catalogue_full_pass","table":"partner_cursors","dimension":"freshness","severity":"warn","weight":2,"baseline":false,"what":"The x402 harvest has not completed a full pass of the catalogue within the window. This is the page-one freeze of September 2026, caught by the machine instead of by a reader.","status":"pass","failing":0,"ms":2},{"id":"registration_from_future","table":"registrations","dimension":"validity","severity":"block","weight":2,"baseline":false,"what":"A registration claims to have been minted in the future.","status":"pass","failing":0,"ms":1},{"id":"waitlist_email_format","table":"waitlist","dimension":"validity","severity":"warn","weight":1,"baseline":false,"what":"A waitlist entry does not look like an email address. Only a hash is returned: this table holds personal data.","status":"pass","failing":0,"ms":2},{"id":"series_not_archived","table":"series","dimension":"completeness","severity":"warn","weight":1,"baseline":false,"what":"A series the site lists is stored on every run but missing from the archive list, so /api/series serves it with no history.","status":"pass","failing":0,"ms":4}]}