@secondlayer/shared 7.3.0 → 7.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/src/db/index.d.ts +36 -1
- package/dist/src/db/index.js +3 -1
- package/dist/src/db/index.js.map +3 -3
- package/dist/src/db/queries/chain-reorgs.d.ts +33 -0
- package/dist/src/db/queries/chain-reorgs.js +3 -1
- package/dist/src/db/queries/chain-reorgs.js.map +3 -3
- package/dist/src/db/queries/contracts.d.ts +33 -0
- package/dist/src/db/queries/integrity.d.ts +59 -1
- package/dist/src/db/queries/integrity.js +26 -1
- package/dist/src/db/queries/integrity.js.map +3 -3
- package/dist/src/db/queries/subgraph-gaps.d.ts +33 -0
- package/dist/src/db/queries/subgraph-operations.d.ts +33 -0
- package/dist/src/db/queries/subgraphs.d.ts +33 -0
- package/dist/src/db/queries/subgraphs.js +3 -1
- package/dist/src/db/queries/subgraphs.js.map +3 -3
- package/dist/src/db/queries/subscriptions.d.ts +33 -0
- package/dist/src/db/schema.d.ts +34 -1
- package/dist/src/errors.d.ts +1 -1
- package/dist/src/errors.js +2 -1
- package/dist/src/errors.js.map +3 -3
- package/dist/src/index-http.d.ts +2 -0
- package/dist/src/index-http.js.map +2 -2
- package/dist/src/index.d.ts +41 -6
- package/dist/src/index.js +4 -1
- package/dist/src/index.js.map +6 -6
- package/dist/src/node/local-client.d.ts +33 -0
- package/dist/src/schemas/index.d.ts +2 -2
- package/dist/src/schemas/index.js.map +1 -1
- package/dist/src/schemas/subgraphs.d.ts +2 -2
- package/dist/src/schemas/subgraphs.js.map +1 -1
- package/dist/src/subgraphs/spec.d.ts +4 -4
- package/dist/src/subgraphs/spec.js.map +1 -1
- package/migrations/0111_chain_read_cache.ts +64 -0
- package/migrations/0112_pending_fork_blocks.ts +52 -0
- package/package.json +6 -3
|
@@ -666,6 +666,37 @@ interface BnsNamespacesTable {
|
|
|
666
666
|
name_count: Generated<number>;
|
|
667
667
|
updated_at: Generated<Date>;
|
|
668
668
|
}
|
|
669
|
+
/**
|
|
670
|
+
* Memoized `ctx.client.readOnly()` results. Keyed on `index_block_hash` so a
|
|
671
|
+
* reorg-replaced block never inherits the orphaned fork's answer; a NULL
|
|
672
|
+
* `index_block_hash` marks a caller-declared contract-constant value, cached
|
|
673
|
+
* once per contract+args instead of once per block.
|
|
674
|
+
*/
|
|
675
|
+
interface ChainReadCacheTable {
|
|
676
|
+
id: Generated<number>;
|
|
677
|
+
contract_id: string;
|
|
678
|
+
function_name: string;
|
|
679
|
+
args_hash: string;
|
|
680
|
+
index_block_hash: string | null;
|
|
681
|
+
block_height: ColumnType<number | null, number | null | undefined, number | null>;
|
|
682
|
+
result_hex: string;
|
|
683
|
+
created_at: Generated<Date>;
|
|
684
|
+
}
|
|
685
|
+
/**
|
|
686
|
+
* A block that arrived for a height we already hold, staged until a later
|
|
687
|
+
* block's `parent_hash` says which of the two the chain kept. See migration
|
|
688
|
+
* 0112 — adopting on first sight picked the losing fork twice.
|
|
689
|
+
*/
|
|
690
|
+
interface PendingForkBlocksTable {
|
|
691
|
+
height: number;
|
|
692
|
+
block_hash: string;
|
|
693
|
+
parent_hash: string;
|
|
694
|
+
/** The canonical hash we held at this height when the contender arrived. */
|
|
695
|
+
incumbent_hash: string;
|
|
696
|
+
/** The raw observer payload, replayed verbatim if this fork wins. */
|
|
697
|
+
payload: ColumnType<unknown, unknown, unknown>;
|
|
698
|
+
received_at: Generated<Date>;
|
|
699
|
+
}
|
|
669
700
|
interface Database {
|
|
670
701
|
blocks: BlocksTable;
|
|
671
702
|
transactions: TransactionsTable;
|
|
@@ -727,6 +758,8 @@ interface Database {
|
|
|
727
758
|
service_heartbeats: ServiceHeartbeatsTable;
|
|
728
759
|
x402_payments: X402PaymentsTable;
|
|
729
760
|
x402_balances: X402BalancesTable;
|
|
761
|
+
chain_read_cache: ChainReadCacheTable;
|
|
762
|
+
pending_fork_blocks: PendingForkBlocksTable;
|
|
730
763
|
}
|
|
731
764
|
/** Prepaid x402 credit — one running USD-micros balance per payer principal. */
|
|
732
765
|
interface X402BalancesTable {
|
|
@@ -666,6 +666,37 @@ interface BnsNamespacesTable {
|
|
|
666
666
|
name_count: Generated<number>;
|
|
667
667
|
updated_at: Generated<Date>;
|
|
668
668
|
}
|
|
669
|
+
/**
|
|
670
|
+
* Memoized `ctx.client.readOnly()` results. Keyed on `index_block_hash` so a
|
|
671
|
+
* reorg-replaced block never inherits the orphaned fork's answer; a NULL
|
|
672
|
+
* `index_block_hash` marks a caller-declared contract-constant value, cached
|
|
673
|
+
* once per contract+args instead of once per block.
|
|
674
|
+
*/
|
|
675
|
+
interface ChainReadCacheTable {
|
|
676
|
+
id: Generated<number>;
|
|
677
|
+
contract_id: string;
|
|
678
|
+
function_name: string;
|
|
679
|
+
args_hash: string;
|
|
680
|
+
index_block_hash: string | null;
|
|
681
|
+
block_height: ColumnType<number | null, number | null | undefined, number | null>;
|
|
682
|
+
result_hex: string;
|
|
683
|
+
created_at: Generated<Date>;
|
|
684
|
+
}
|
|
685
|
+
/**
|
|
686
|
+
* A block that arrived for a height we already hold, staged until a later
|
|
687
|
+
* block's `parent_hash` says which of the two the chain kept. See migration
|
|
688
|
+
* 0112 — adopting on first sight picked the losing fork twice.
|
|
689
|
+
*/
|
|
690
|
+
interface PendingForkBlocksTable {
|
|
691
|
+
height: number;
|
|
692
|
+
block_hash: string;
|
|
693
|
+
parent_hash: string;
|
|
694
|
+
/** The canonical hash we held at this height when the contender arrived. */
|
|
695
|
+
incumbent_hash: string;
|
|
696
|
+
/** The raw observer payload, replayed verbatim if this fork wins. */
|
|
697
|
+
payload: ColumnType<unknown, unknown, unknown>;
|
|
698
|
+
received_at: Generated<Date>;
|
|
699
|
+
}
|
|
669
700
|
interface Database {
|
|
670
701
|
blocks: BlocksTable;
|
|
671
702
|
transactions: TransactionsTable;
|
|
@@ -727,6 +758,8 @@ interface Database {
|
|
|
727
758
|
service_heartbeats: ServiceHeartbeatsTable;
|
|
728
759
|
x402_payments: X402PaymentsTable;
|
|
729
760
|
x402_balances: X402BalancesTable;
|
|
761
|
+
chain_read_cache: ChainReadCacheTable;
|
|
762
|
+
pending_fork_blocks: PendingForkBlocksTable;
|
|
730
763
|
}
|
|
731
764
|
/** Prepaid x402 credit — one running USD-micros balance per payer principal. */
|
|
732
765
|
interface X402BalancesTable {
|
|
@@ -969,4 +1002,29 @@ declare function checkChainDataIntegrity(db: Kysely<Database>, opts?: {
|
|
|
969
1002
|
lookback?: number
|
|
970
1003
|
}): Promise<ChainDataIntegrity>;
|
|
971
1004
|
declare function computeContiguousTip(db: Kysely<Database>, fromHeight: number): Promise<number>;
|
|
972
|
-
|
|
1005
|
+
type BrokenLink = {
|
|
1006
|
+
height: number
|
|
1007
|
+
hash: string
|
|
1008
|
+
expectedParent: string
|
|
1009
|
+
storedParent: string
|
|
1010
|
+
};
|
|
1011
|
+
/**
|
|
1012
|
+
* Canonical heights whose block does not descend from the canonical block
|
|
1013
|
+
* below it.
|
|
1014
|
+
*
|
|
1015
|
+
* `findGaps` asks "is every height present?", which a chain sitting on a losing
|
|
1016
|
+
* fork answers yes to. On 2026-07-30 a reorg at 8,663,166 was resolved the
|
|
1017
|
+
* wrong way: we adopted a block that mainnet orphaned, its true successors were
|
|
1018
|
+
* swept non-canonical, and later blocks were inserted canonical on top. Every
|
|
1019
|
+
* height existed. Nothing was "missing". The chain simply did not join up, and
|
|
1020
|
+
* no check asked that question — so we served a broken chain for seventeen
|
|
1021
|
+
* hours and only noticed because subgraphs stopped moving.
|
|
1022
|
+
*
|
|
1023
|
+
* Scoped to a recent window by default: an unlinked height is an active-repair
|
|
1024
|
+
* concern, and scanning eight million rows every cycle is not.
|
|
1025
|
+
*/
|
|
1026
|
+
declare function findBrokenLinks(db: Kysely<Database>, opts?: {
|
|
1027
|
+
window?: number
|
|
1028
|
+
limit?: number
|
|
1029
|
+
}): Promise<BrokenLink[]>;
|
|
1030
|
+
export { findGaps, findBrokenLinks, countMissingBlocks, computeContiguousTip, checkChainDataIntegrity, Gap, ChainDataIntegrity, BrokenLink };
|
|
@@ -92,12 +92,37 @@ async function computeContiguousTip(db, fromHeight) {
|
|
|
92
92
|
`.execute(db);
|
|
93
93
|
return Number(rows[0]?.tip ?? fromHeight);
|
|
94
94
|
}
|
|
95
|
+
async function findBrokenLinks(db, opts = {}) {
|
|
96
|
+
const windowSize = opts.window ?? 1e4;
|
|
97
|
+
const limitClause = opts.limit ? sql`LIMIT ${opts.limit}` : sql``;
|
|
98
|
+
const { rows } = await sql`
|
|
99
|
+
WITH recent AS (
|
|
100
|
+
SELECT height, hash, parent_hash
|
|
101
|
+
FROM blocks
|
|
102
|
+
WHERE canonical = true
|
|
103
|
+
AND height > (SELECT MAX(height) - ${windowSize} FROM blocks WHERE canonical = true)
|
|
104
|
+
)
|
|
105
|
+
SELECT b.height, b.hash, p.hash AS expected_parent, b.parent_hash AS stored_parent
|
|
106
|
+
FROM recent b
|
|
107
|
+
JOIN recent p ON p.height = b.height - 1
|
|
108
|
+
WHERE b.parent_hash <> p.hash
|
|
109
|
+
ORDER BY b.height
|
|
110
|
+
${limitClause}
|
|
111
|
+
`.execute(db);
|
|
112
|
+
return rows.map((r) => ({
|
|
113
|
+
height: Number(r.height),
|
|
114
|
+
hash: r.hash,
|
|
115
|
+
expectedParent: r.expected_parent,
|
|
116
|
+
storedParent: r.stored_parent
|
|
117
|
+
}));
|
|
118
|
+
}
|
|
95
119
|
export {
|
|
96
120
|
findGaps,
|
|
121
|
+
findBrokenLinks,
|
|
97
122
|
countMissingBlocks,
|
|
98
123
|
computeContiguousTip,
|
|
99
124
|
checkChainDataIntegrity
|
|
100
125
|
};
|
|
101
126
|
|
|
102
|
-
//# debugId=
|
|
127
|
+
//# debugId=FFA2BEF866239EA364756E2164756E21
|
|
103
128
|
//# sourceMappingURL=integrity.js.map
|
|
@@ -2,9 +2,9 @@
|
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../src/db/queries/integrity.ts"],
|
|
4
4
|
"sourcesContent": [
|
|
5
|
-
"import { type Kysely, sql } from \"kysely\";\nimport type { Database } from \"../types.ts\";\n\nexport interface Gap {\n\tgapStart: number;\n\tgapEnd: number;\n\tsize: number;\n}\n\nexport async function findGaps(\n\tdb: Kysely<Database>,\n\tlimit?: number,\n): Promise<Gap[]> {\n\tconst limitClause = limit ? sql`LIMIT ${limit}` : sql``;\n\tconst { rows } = await sql<{\n\t\tgap_start: string;\n\t\tgap_end: string;\n\t\tsize: string;\n\t}>`\n SELECT gap_start, gap_end, gap_end - gap_start + 1 AS size\n FROM (\n SELECT height + 1 AS gap_start, next_height - 1 AS gap_end\n FROM (\n SELECT height, LEAD(height) OVER (ORDER BY height) AS next_height\n FROM blocks WHERE canonical = true\n ) sub\n WHERE next_height - height > 1\n ) gaps\n ORDER BY gap_start\n ${limitClause}\n `.execute(db);\n\n\treturn rows.map((r) => ({\n\t\tgapStart: Number(r.gap_start),\n\t\tgapEnd: Number(r.gap_end),\n\t\tsize: Number(r.size),\n\t}));\n}\n\nexport async function countMissingBlocks(\n\tdb: Kysely<Database>,\n): Promise<number> {\n\tconst { rows } = await sql<{ total: string }>`\n SELECT COALESCE(SUM(next_height - height - 1), 0) AS total\n FROM (\n SELECT height, LEAD(height) OVER (ORDER BY height) AS next_height\n FROM blocks WHERE canonical = true\n ) sub\n WHERE next_height - height > 1\n `.execute(db);\n\n\treturn Number(rows[0]?.total ?? 0);\n}\n\nexport interface ChainDataIntegrity {\n\tok: boolean;\n\tmaxHeight: number;\n\tsampleHeight: number | null;\n\tsampleBlocks: number;\n\treason: string | null;\n}\n\n/**\n * Cheap sanity check that the `blocks` table actually holds the history its tip\n * implies. Catches a wrong/empty Postgres volume — e.g. a container recreated\n * against a fresh volume — being silently served: if the tip is high but a\n * window of blocks well below it is missing, the data isn't what the tip claims.\n *\n * Below `checkFloor` we can't distinguish a fresh install from an empty volume,\n * so we report ok — a genuinely new DB legitimately has little history. Two\n * indexed lookups, safe to run on every startup / health poll.\n */\nexport async function checkChainDataIntegrity(\n\tdb: Kysely<Database>,\n\topts?: { checkFloor?: number; lookback?: number },\n): Promise<ChainDataIntegrity> {\n\tconst checkFloor = opts?.checkFloor ?? 1_000_000;\n\tconst lookback = opts?.lookback ?? 500_000;\n\n\tconst { rows: tipRows } = await sql<{ max: string | null }>`\n\t\tSELECT MAX(height) AS max FROM blocks WHERE canonical = true\n\t`.execute(db);\n\tconst maxHeight = Number(tipRows[0]?.max ?? 0);\n\n\tif (maxHeight < checkFloor) {\n\t\treturn {\n\t\t\tok: true,\n\t\t\tmaxHeight,\n\t\t\tsampleHeight: null,\n\t\t\tsampleBlocks: 0,\n\t\t\treason: null,\n\t\t};\n\t}\n\n\tconst sampleHeight = maxHeight - lookback;\n\tconst { rows: sampleRows } = await sql<{ n: string }>`\n\t\tSELECT count(*) AS n FROM blocks\n\t\tWHERE canonical = true AND height >= ${sampleHeight} AND height < ${sampleHeight + 1000}\n\t`.execute(db);\n\tconst sampleBlocks = Number(sampleRows[0]?.n ?? 0);\n\n\treturn {\n\t\tok: sampleBlocks > 0,\n\t\tmaxHeight,\n\t\tsampleHeight,\n\t\tsampleBlocks,\n\t\treason:\n\t\t\tsampleBlocks > 0\n\t\t\t\t? null\n\t\t\t\t: `tip is ${maxHeight} but no canonical blocks near ${sampleHeight} — wrong or empty volume?`,\n\t};\n}\n\nexport async function computeContiguousTip(\n\tdb: Kysely<Database>,\n\tfromHeight: number,\n): Promise<number> {\n\tconst { rows } = await sql<{ tip: string }>`\n SELECT COALESCE(MAX(height), ${fromHeight}) AS tip\n FROM (\n SELECT height, height - ROW_NUMBER() OVER (ORDER BY height) AS grp\n FROM blocks WHERE canonical = true AND height >= ${fromHeight}\n ) sub\n WHERE grp = (\n SELECT height - ROW_NUMBER() OVER (ORDER BY height)\n FROM blocks WHERE canonical = true AND height = ${fromHeight}\n )\n `.execute(db);\n\n\treturn Number(rows[0]?.tip ?? fromHeight);\n}\n"
|
|
5
|
+
"import { type Kysely, sql } from \"kysely\";\nimport type { Database } from \"../types.ts\";\n\nexport interface Gap {\n\tgapStart: number;\n\tgapEnd: number;\n\tsize: number;\n}\n\nexport async function findGaps(\n\tdb: Kysely<Database>,\n\tlimit?: number,\n): Promise<Gap[]> {\n\tconst limitClause = limit ? sql`LIMIT ${limit}` : sql``;\n\tconst { rows } = await sql<{\n\t\tgap_start: string;\n\t\tgap_end: string;\n\t\tsize: string;\n\t}>`\n SELECT gap_start, gap_end, gap_end - gap_start + 1 AS size\n FROM (\n SELECT height + 1 AS gap_start, next_height - 1 AS gap_end\n FROM (\n SELECT height, LEAD(height) OVER (ORDER BY height) AS next_height\n FROM blocks WHERE canonical = true\n ) sub\n WHERE next_height - height > 1\n ) gaps\n ORDER BY gap_start\n ${limitClause}\n `.execute(db);\n\n\treturn rows.map((r) => ({\n\t\tgapStart: Number(r.gap_start),\n\t\tgapEnd: Number(r.gap_end),\n\t\tsize: Number(r.size),\n\t}));\n}\n\nexport async function countMissingBlocks(\n\tdb: Kysely<Database>,\n): Promise<number> {\n\tconst { rows } = await sql<{ total: string }>`\n SELECT COALESCE(SUM(next_height - height - 1), 0) AS total\n FROM (\n SELECT height, LEAD(height) OVER (ORDER BY height) AS next_height\n FROM blocks WHERE canonical = true\n ) sub\n WHERE next_height - height > 1\n `.execute(db);\n\n\treturn Number(rows[0]?.total ?? 0);\n}\n\nexport interface ChainDataIntegrity {\n\tok: boolean;\n\tmaxHeight: number;\n\tsampleHeight: number | null;\n\tsampleBlocks: number;\n\treason: string | null;\n}\n\n/**\n * Cheap sanity check that the `blocks` table actually holds the history its tip\n * implies. Catches a wrong/empty Postgres volume — e.g. a container recreated\n * against a fresh volume — being silently served: if the tip is high but a\n * window of blocks well below it is missing, the data isn't what the tip claims.\n *\n * Below `checkFloor` we can't distinguish a fresh install from an empty volume,\n * so we report ok — a genuinely new DB legitimately has little history. Two\n * indexed lookups, safe to run on every startup / health poll.\n */\nexport async function checkChainDataIntegrity(\n\tdb: Kysely<Database>,\n\topts?: { checkFloor?: number; lookback?: number },\n): Promise<ChainDataIntegrity> {\n\tconst checkFloor = opts?.checkFloor ?? 1_000_000;\n\tconst lookback = opts?.lookback ?? 500_000;\n\n\tconst { rows: tipRows } = await sql<{ max: string | null }>`\n\t\tSELECT MAX(height) AS max FROM blocks WHERE canonical = true\n\t`.execute(db);\n\tconst maxHeight = Number(tipRows[0]?.max ?? 0);\n\n\tif (maxHeight < checkFloor) {\n\t\treturn {\n\t\t\tok: true,\n\t\t\tmaxHeight,\n\t\t\tsampleHeight: null,\n\t\t\tsampleBlocks: 0,\n\t\t\treason: null,\n\t\t};\n\t}\n\n\tconst sampleHeight = maxHeight - lookback;\n\tconst { rows: sampleRows } = await sql<{ n: string }>`\n\t\tSELECT count(*) AS n FROM blocks\n\t\tWHERE canonical = true AND height >= ${sampleHeight} AND height < ${sampleHeight + 1000}\n\t`.execute(db);\n\tconst sampleBlocks = Number(sampleRows[0]?.n ?? 0);\n\n\treturn {\n\t\tok: sampleBlocks > 0,\n\t\tmaxHeight,\n\t\tsampleHeight,\n\t\tsampleBlocks,\n\t\treason:\n\t\t\tsampleBlocks > 0\n\t\t\t\t? null\n\t\t\t\t: `tip is ${maxHeight} but no canonical blocks near ${sampleHeight} — wrong or empty volume?`,\n\t};\n}\n\nexport async function computeContiguousTip(\n\tdb: Kysely<Database>,\n\tfromHeight: number,\n): Promise<number> {\n\tconst { rows } = await sql<{ tip: string }>`\n SELECT COALESCE(MAX(height), ${fromHeight}) AS tip\n FROM (\n SELECT height, height - ROW_NUMBER() OVER (ORDER BY height) AS grp\n FROM blocks WHERE canonical = true AND height >= ${fromHeight}\n ) sub\n WHERE grp = (\n SELECT height - ROW_NUMBER() OVER (ORDER BY height)\n FROM blocks WHERE canonical = true AND height = ${fromHeight}\n )\n `.execute(db);\n\n\treturn Number(rows[0]?.tip ?? fromHeight);\n}\n\nexport type BrokenLink = {\n\theight: number;\n\thash: string;\n\texpectedParent: string;\n\tstoredParent: string;\n};\n\n/**\n * Canonical heights whose block does not descend from the canonical block\n * below it.\n *\n * `findGaps` asks \"is every height present?\", which a chain sitting on a losing\n * fork answers yes to. On 2026-07-30 a reorg at 8,663,166 was resolved the\n * wrong way: we adopted a block that mainnet orphaned, its true successors were\n * swept non-canonical, and later blocks were inserted canonical on top. Every\n * height existed. Nothing was \"missing\". The chain simply did not join up, and\n * no check asked that question — so we served a broken chain for seventeen\n * hours and only noticed because subgraphs stopped moving.\n *\n * Scoped to a recent window by default: an unlinked height is an active-repair\n * concern, and scanning eight million rows every cycle is not.\n */\nexport async function findBrokenLinks(\n\tdb: Kysely<Database>,\n\topts: { window?: number; limit?: number } = {},\n): Promise<BrokenLink[]> {\n\tconst windowSize = opts.window ?? 10_000;\n\tconst limitClause = opts.limit ? sql`LIMIT ${opts.limit}` : sql``;\n\tconst { rows } = await sql<{\n\t\theight: string | number;\n\t\thash: string;\n\t\texpected_parent: string;\n\t\tstored_parent: string;\n\t}>`\n\t\tWITH recent AS (\n\t\t\tSELECT height, hash, parent_hash\n\t\t\tFROM blocks\n\t\t\tWHERE canonical = true\n\t\t\t\tAND height > (SELECT MAX(height) - ${windowSize} FROM blocks WHERE canonical = true)\n\t\t)\n\t\tSELECT b.height, b.hash, p.hash AS expected_parent, b.parent_hash AS stored_parent\n\t\tFROM recent b\n\t\tJOIN recent p ON p.height = b.height - 1\n\t\tWHERE b.parent_hash <> p.hash\n\t\tORDER BY b.height\n\t\t${limitClause}\n\t`.execute(db);\n\treturn rows.map((r) => ({\n\t\theight: Number(r.height),\n\t\thash: r.hash,\n\t\texpectedParent: r.expected_parent,\n\t\tstoredParent: r.stored_parent,\n\t}));\n}\n"
|
|
6
6
|
],
|
|
7
|
-
"mappings": ";;;;;;;;;;;;;;;;;AAAA;AASA,eAAsB,QAAQ,CAC7B,IACA,OACiB;AAAA,EACjB,MAAM,cAAc,QAAQ,YAAY,UAAU;AAAA,EAClD,QAAQ,SAAS,MAAM;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,MAelB;AAAA,IACF,QAAQ,EAAE;AAAA,EAEb,OAAO,KAAK,IAAI,CAAC,OAAO;AAAA,IACvB,UAAU,OAAO,EAAE,SAAS;AAAA,IAC5B,QAAQ,OAAO,EAAE,OAAO;AAAA,IACxB,MAAM,OAAO,EAAE,IAAI;AAAA,EACpB,EAAE;AAAA;AAGH,eAAsB,kBAAkB,CACvC,IACkB;AAAA,EAClB,QAAQ,SAAS,MAAM;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,IAOpB,QAAQ,EAAE;AAAA,EAEb,OAAO,OAAO,KAAK,IAAI,SAAS,CAAC;AAAA;AAqBlC,eAAsB,uBAAuB,CAC5C,IACA,MAC8B;AAAA,EAC9B,MAAM,aAAa,MAAM,cAAc;AAAA,EACvC,MAAM,WAAW,MAAM,YAAY;AAAA,EAEnC,QAAQ,MAAM,YAAY,MAAM;AAAA;AAAA,GAE9B,QAAQ,EAAE;AAAA,EACZ,MAAM,YAAY,OAAO,QAAQ,IAAI,OAAO,CAAC;AAAA,EAE7C,IAAI,YAAY,YAAY;AAAA,IAC3B,OAAO;AAAA,MACN,IAAI;AAAA,MACJ;AAAA,MACA,cAAc;AAAA,MACd,cAAc;AAAA,MACd,QAAQ;AAAA,IACT;AAAA,EACD;AAAA,EAEA,MAAM,eAAe,YAAY;AAAA,EACjC,QAAQ,MAAM,eAAe,MAAM;AAAA;AAAA,yCAEK,6BAA6B,eAAe;AAAA,GAClF,QAAQ,EAAE;AAAA,EACZ,MAAM,eAAe,OAAO,WAAW,IAAI,KAAK,CAAC;AAAA,EAEjD,OAAO;AAAA,IACN,IAAI,eAAe;AAAA,IACnB;AAAA,IACA;AAAA,IACA;AAAA,IACA,QACC,eAAe,IACZ,OACA,UAAU,0CAA0C;AAAA,EACzD;AAAA;AAGD,eAAsB,oBAAoB,CACzC,IACA,YACkB;AAAA,EAClB,QAAQ,SAAS,MAAM;AAAA,mCACW;AAAA;AAAA;AAAA,yDAGsB;AAAA;AAAA;AAAA;AAAA,wDAID;AAAA;AAAA,IAEpD,QAAQ,EAAE;AAAA,EAEb,OAAO,OAAO,KAAK,IAAI,OAAO,UAAU;AAAA;",
|
|
8
|
-
"debugId": "
|
|
7
|
+
"mappings": ";;;;;;;;;;;;;;;;;AAAA;AASA,eAAsB,QAAQ,CAC7B,IACA,OACiB;AAAA,EACjB,MAAM,cAAc,QAAQ,YAAY,UAAU;AAAA,EAClD,QAAQ,SAAS,MAAM;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,MAelB;AAAA,IACF,QAAQ,EAAE;AAAA,EAEb,OAAO,KAAK,IAAI,CAAC,OAAO;AAAA,IACvB,UAAU,OAAO,EAAE,SAAS;AAAA,IAC5B,QAAQ,OAAO,EAAE,OAAO;AAAA,IACxB,MAAM,OAAO,EAAE,IAAI;AAAA,EACpB,EAAE;AAAA;AAGH,eAAsB,kBAAkB,CACvC,IACkB;AAAA,EAClB,QAAQ,SAAS,MAAM;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,IAOpB,QAAQ,EAAE;AAAA,EAEb,OAAO,OAAO,KAAK,IAAI,SAAS,CAAC;AAAA;AAqBlC,eAAsB,uBAAuB,CAC5C,IACA,MAC8B;AAAA,EAC9B,MAAM,aAAa,MAAM,cAAc;AAAA,EACvC,MAAM,WAAW,MAAM,YAAY;AAAA,EAEnC,QAAQ,MAAM,YAAY,MAAM;AAAA;AAAA,GAE9B,QAAQ,EAAE;AAAA,EACZ,MAAM,YAAY,OAAO,QAAQ,IAAI,OAAO,CAAC;AAAA,EAE7C,IAAI,YAAY,YAAY;AAAA,IAC3B,OAAO;AAAA,MACN,IAAI;AAAA,MACJ;AAAA,MACA,cAAc;AAAA,MACd,cAAc;AAAA,MACd,QAAQ;AAAA,IACT;AAAA,EACD;AAAA,EAEA,MAAM,eAAe,YAAY;AAAA,EACjC,QAAQ,MAAM,eAAe,MAAM;AAAA;AAAA,yCAEK,6BAA6B,eAAe;AAAA,GAClF,QAAQ,EAAE;AAAA,EACZ,MAAM,eAAe,OAAO,WAAW,IAAI,KAAK,CAAC;AAAA,EAEjD,OAAO;AAAA,IACN,IAAI,eAAe;AAAA,IACnB;AAAA,IACA;AAAA,IACA;AAAA,IACA,QACC,eAAe,IACZ,OACA,UAAU,0CAA0C;AAAA,EACzD;AAAA;AAGD,eAAsB,oBAAoB,CACzC,IACA,YACkB;AAAA,EAClB,QAAQ,SAAS,MAAM;AAAA,mCACW;AAAA;AAAA;AAAA,yDAGsB;AAAA;AAAA;AAAA;AAAA,wDAID;AAAA;AAAA,IAEpD,QAAQ,EAAE;AAAA,EAEb,OAAO,OAAO,KAAK,IAAI,OAAO,UAAU;AAAA;AAyBzC,eAAsB,eAAe,CACpC,IACA,OAA4C,CAAC,GACrB;AAAA,EACxB,MAAM,aAAa,KAAK,UAAU;AAAA,EAClC,MAAM,cAAc,KAAK,QAAQ,YAAY,KAAK,UAAU;AAAA,EAC5D,QAAQ,SAAS,MAAM;AAAA;AAAA;AAAA;AAAA;AAAA,yCAUiB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,IAOrC;AAAA,GACD,QAAQ,EAAE;AAAA,EACZ,OAAO,KAAK,IAAI,CAAC,OAAO;AAAA,IACvB,QAAQ,OAAO,EAAE,MAAM;AAAA,IACvB,MAAM,EAAE;AAAA,IACR,gBAAgB,EAAE;AAAA,IAClB,cAAc,EAAE;AAAA,EACjB,EAAE;AAAA;",
|
|
8
|
+
"debugId": "FFA2BEF866239EA364756E2164756E21",
|
|
9
9
|
"names": []
|
|
10
10
|
}
|
|
@@ -666,6 +666,37 @@ interface BnsNamespacesTable {
|
|
|
666
666
|
name_count: Generated<number>;
|
|
667
667
|
updated_at: Generated<Date>;
|
|
668
668
|
}
|
|
669
|
+
/**
|
|
670
|
+
* Memoized `ctx.client.readOnly()` results. Keyed on `index_block_hash` so a
|
|
671
|
+
* reorg-replaced block never inherits the orphaned fork's answer; a NULL
|
|
672
|
+
* `index_block_hash` marks a caller-declared contract-constant value, cached
|
|
673
|
+
* once per contract+args instead of once per block.
|
|
674
|
+
*/
|
|
675
|
+
interface ChainReadCacheTable {
|
|
676
|
+
id: Generated<number>;
|
|
677
|
+
contract_id: string;
|
|
678
|
+
function_name: string;
|
|
679
|
+
args_hash: string;
|
|
680
|
+
index_block_hash: string | null;
|
|
681
|
+
block_height: ColumnType<number | null, number | null | undefined, number | null>;
|
|
682
|
+
result_hex: string;
|
|
683
|
+
created_at: Generated<Date>;
|
|
684
|
+
}
|
|
685
|
+
/**
|
|
686
|
+
* A block that arrived for a height we already hold, staged until a later
|
|
687
|
+
* block's `parent_hash` says which of the two the chain kept. See migration
|
|
688
|
+
* 0112 — adopting on first sight picked the losing fork twice.
|
|
689
|
+
*/
|
|
690
|
+
interface PendingForkBlocksTable {
|
|
691
|
+
height: number;
|
|
692
|
+
block_hash: string;
|
|
693
|
+
parent_hash: string;
|
|
694
|
+
/** The canonical hash we held at this height when the contender arrived. */
|
|
695
|
+
incumbent_hash: string;
|
|
696
|
+
/** The raw observer payload, replayed verbatim if this fork wins. */
|
|
697
|
+
payload: ColumnType<unknown, unknown, unknown>;
|
|
698
|
+
received_at: Generated<Date>;
|
|
699
|
+
}
|
|
669
700
|
interface Database {
|
|
670
701
|
blocks: BlocksTable;
|
|
671
702
|
transactions: TransactionsTable;
|
|
@@ -727,6 +758,8 @@ interface Database {
|
|
|
727
758
|
service_heartbeats: ServiceHeartbeatsTable;
|
|
728
759
|
x402_payments: X402PaymentsTable;
|
|
729
760
|
x402_balances: X402BalancesTable;
|
|
761
|
+
chain_read_cache: ChainReadCacheTable;
|
|
762
|
+
pending_fork_blocks: PendingForkBlocksTable;
|
|
730
763
|
}
|
|
731
764
|
/** Prepaid x402 credit — one running USD-micros balance per payer principal. */
|
|
732
765
|
interface X402BalancesTable {
|
|
@@ -666,6 +666,37 @@ interface BnsNamespacesTable {
|
|
|
666
666
|
name_count: Generated<number>;
|
|
667
667
|
updated_at: Generated<Date>;
|
|
668
668
|
}
|
|
669
|
+
/**
|
|
670
|
+
* Memoized `ctx.client.readOnly()` results. Keyed on `index_block_hash` so a
|
|
671
|
+
* reorg-replaced block never inherits the orphaned fork's answer; a NULL
|
|
672
|
+
* `index_block_hash` marks a caller-declared contract-constant value, cached
|
|
673
|
+
* once per contract+args instead of once per block.
|
|
674
|
+
*/
|
|
675
|
+
interface ChainReadCacheTable {
|
|
676
|
+
id: Generated<number>;
|
|
677
|
+
contract_id: string;
|
|
678
|
+
function_name: string;
|
|
679
|
+
args_hash: string;
|
|
680
|
+
index_block_hash: string | null;
|
|
681
|
+
block_height: ColumnType<number | null, number | null | undefined, number | null>;
|
|
682
|
+
result_hex: string;
|
|
683
|
+
created_at: Generated<Date>;
|
|
684
|
+
}
|
|
685
|
+
/**
|
|
686
|
+
* A block that arrived for a height we already hold, staged until a later
|
|
687
|
+
* block's `parent_hash` says which of the two the chain kept. See migration
|
|
688
|
+
* 0112 — adopting on first sight picked the losing fork twice.
|
|
689
|
+
*/
|
|
690
|
+
interface PendingForkBlocksTable {
|
|
691
|
+
height: number;
|
|
692
|
+
block_hash: string;
|
|
693
|
+
parent_hash: string;
|
|
694
|
+
/** The canonical hash we held at this height when the contender arrived. */
|
|
695
|
+
incumbent_hash: string;
|
|
696
|
+
/** The raw observer payload, replayed verbatim if this fork wins. */
|
|
697
|
+
payload: ColumnType<unknown, unknown, unknown>;
|
|
698
|
+
received_at: Generated<Date>;
|
|
699
|
+
}
|
|
669
700
|
interface Database {
|
|
670
701
|
blocks: BlocksTable;
|
|
671
702
|
transactions: TransactionsTable;
|
|
@@ -727,6 +758,8 @@ interface Database {
|
|
|
727
758
|
service_heartbeats: ServiceHeartbeatsTable;
|
|
728
759
|
x402_payments: X402PaymentsTable;
|
|
729
760
|
x402_balances: X402BalancesTable;
|
|
761
|
+
chain_read_cache: ChainReadCacheTable;
|
|
762
|
+
pending_fork_blocks: PendingForkBlocksTable;
|
|
730
763
|
}
|
|
731
764
|
/** Prepaid x402 credit — one running USD-micros balance per payer principal. */
|
|
732
765
|
interface X402BalancesTable {
|
|
@@ -667,6 +667,37 @@ interface BnsNamespacesTable {
|
|
|
667
667
|
name_count: Generated<number>;
|
|
668
668
|
updated_at: Generated<Date>;
|
|
669
669
|
}
|
|
670
|
+
/**
|
|
671
|
+
* Memoized `ctx.client.readOnly()` results. Keyed on `index_block_hash` so a
|
|
672
|
+
* reorg-replaced block never inherits the orphaned fork's answer; a NULL
|
|
673
|
+
* `index_block_hash` marks a caller-declared contract-constant value, cached
|
|
674
|
+
* once per contract+args instead of once per block.
|
|
675
|
+
*/
|
|
676
|
+
interface ChainReadCacheTable {
|
|
677
|
+
id: Generated<number>;
|
|
678
|
+
contract_id: string;
|
|
679
|
+
function_name: string;
|
|
680
|
+
args_hash: string;
|
|
681
|
+
index_block_hash: string | null;
|
|
682
|
+
block_height: ColumnType<number | null, number | null | undefined, number | null>;
|
|
683
|
+
result_hex: string;
|
|
684
|
+
created_at: Generated<Date>;
|
|
685
|
+
}
|
|
686
|
+
/**
|
|
687
|
+
* A block that arrived for a height we already hold, staged until a later
|
|
688
|
+
* block's `parent_hash` says which of the two the chain kept. See migration
|
|
689
|
+
* 0112 — adopting on first sight picked the losing fork twice.
|
|
690
|
+
*/
|
|
691
|
+
interface PendingForkBlocksTable {
|
|
692
|
+
height: number;
|
|
693
|
+
block_hash: string;
|
|
694
|
+
parent_hash: string;
|
|
695
|
+
/** The canonical hash we held at this height when the contender arrived. */
|
|
696
|
+
incumbent_hash: string;
|
|
697
|
+
/** The raw observer payload, replayed verbatim if this fork wins. */
|
|
698
|
+
payload: ColumnType<unknown, unknown, unknown>;
|
|
699
|
+
received_at: Generated<Date>;
|
|
700
|
+
}
|
|
670
701
|
interface Database {
|
|
671
702
|
blocks: BlocksTable;
|
|
672
703
|
transactions: TransactionsTable;
|
|
@@ -728,6 +759,8 @@ interface Database {
|
|
|
728
759
|
service_heartbeats: ServiceHeartbeatsTable;
|
|
729
760
|
x402_payments: X402PaymentsTable;
|
|
730
761
|
x402_balances: X402BalancesTable;
|
|
762
|
+
chain_read_cache: ChainReadCacheTable;
|
|
763
|
+
pending_fork_blocks: PendingForkBlocksTable;
|
|
731
764
|
}
|
|
732
765
|
/** Prepaid x402 credit — one running USD-micros balance per payer principal. */
|
|
733
766
|
interface X402BalancesTable {
|
|
@@ -656,6 +656,8 @@ var TABLE_TO_DB = {
|
|
|
656
656
|
index_progress: "source",
|
|
657
657
|
contracts: "source",
|
|
658
658
|
chain_reorgs: "source",
|
|
659
|
+
chain_read_cache: "source",
|
|
660
|
+
pending_fork_blocks: "source",
|
|
659
661
|
decoded_events: "source",
|
|
660
662
|
decoder_checkpoints: "source",
|
|
661
663
|
pox4_calls: "source",
|
|
@@ -1155,5 +1157,5 @@ export {
|
|
|
1155
1157
|
deleteSubgraph
|
|
1156
1158
|
};
|
|
1157
1159
|
|
|
1158
|
-
//# debugId=
|
|
1160
|
+
//# debugId=EB2E9A3BA7B8FF6964756E2164756E21
|
|
1159
1161
|
//# sourceMappingURL=subgraphs.js.map
|