@secondlayer/subgraphs 0.11.1 → 0.11.3

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/index.js CHANGED
@@ -102,7 +102,11 @@ class SubgraphContext {
102
102
  }
103
103
  insert(table, row) {
104
104
  this.validateTable(table);
105
- this.ops.push({ kind: "insert", table, data: row });
105
+ this.ops.push({
106
+ kind: "insert",
107
+ table,
108
+ data: { ...row, _block_height: this.block.height, _tx_id: this._tx.txId }
109
+ });
106
110
  }
107
111
  update(table, where, set) {
108
112
  this.validateTable(table);
@@ -111,13 +115,16 @@ class SubgraphContext {
111
115
  upsert(table, key, row) {
112
116
  this.validateTable(table);
113
117
  const tableDef = this.subgraphSchema[table];
118
+ if (!tableDef)
119
+ return;
114
120
  const keyColumns = Object.keys(key);
115
121
  const hasUniqueConstraint = tableDef.uniqueKeys?.some((uk) => uk.length === keyColumns.length && uk.every((c) => keyColumns.includes(c)));
122
+ const meta = { _block_height: this.block.height, _tx_id: this._tx.txId };
116
123
  if (hasUniqueConstraint) {
117
124
  this.ops.push({
118
125
  kind: "insert",
119
126
  table,
120
- data: { ...key, ...row, _upsert_keys: keyColumns }
127
+ data: { ...key, ...row, ...meta, _upsert_keys: keyColumns }
121
128
  });
122
129
  } else {
123
130
  logger.warn("upsert called without matching uniqueKeys constraint, using fallback", {
@@ -130,6 +137,7 @@ class SubgraphContext {
130
137
  data: {
131
138
  ...key,
132
139
  ...row,
140
+ ...meta,
133
141
  _upsert_fallback_keys: keyColumns,
134
142
  _upsert_fallback_set: row
135
143
  }
@@ -249,11 +257,13 @@ class SubgraphContext {
249
257
  prepareInsert(op) {
250
258
  const upsertKeys = op.data._upsert_keys;
251
259
  const data = { ...op.data };
252
- delete data._upsert_keys;
253
- delete data._upsert_fallback_keys;
254
- delete data._upsert_fallback_set;
255
- data._block_height = this.block.height;
256
- data._tx_id = this._tx.txId;
260
+ data._upsert_keys = undefined;
261
+ data._upsert_fallback_keys = undefined;
262
+ data._upsert_fallback_set = undefined;
263
+ if (!data._block_height)
264
+ data._block_height = this.block.height;
265
+ if (!data._tx_id)
266
+ data._tx_id = this._tx.txId;
257
267
  data._created_at = "NOW()";
258
268
  const cols = Object.keys(data);
259
269
  cols.forEach(validateColumnName);
@@ -268,11 +278,13 @@ class SubgraphContext {
268
278
  const flushInsertBatch = () => {
269
279
  if (!currentBatch)
270
280
  return;
271
- const qualifiedTable = `"${this.pgSchemaName}"."${currentBatch.table}"`;
272
- const colList = currentBatch.cols.map((c) => `"${c}"`).join(", ");
273
- let rows = currentBatch.rows;
274
- if (currentBatch.upsertKeys && currentBatch.upsertKeys.length > 0) {
275
- const keyIndices = currentBatch.upsertKeys.map((k) => currentBatch.cols.indexOf(k));
281
+ const batch = currentBatch;
282
+ const qualifiedTable = `"${this.pgSchemaName}"."${batch.table}"`;
283
+ const colList = batch.cols.map((c) => `"${c}"`).join(", ");
284
+ let rows = batch.rows;
285
+ if (batch.upsertKeys && batch.upsertKeys.length > 0) {
286
+ const uKeys = batch.upsertKeys;
287
+ const keyIndices = uKeys.map((k) => batch.cols.indexOf(k));
276
288
  const seen = new Map;
277
289
  for (let i = 0;i < rows.length; i++) {
278
290
  const key = keyIndices.map((ki) => rows[i][ki]).join("\x00");
@@ -284,13 +296,14 @@ class SubgraphContext {
284
296
  }
285
297
  const valuesList = rows.map((r) => `(${r.join(", ")})`).join(", ");
286
298
  let stmt = `INSERT INTO ${qualifiedTable} (${colList}) VALUES ${valuesList}`;
287
- if (currentBatch.upsertKeys && currentBatch.upsertKeys.length > 0) {
288
- const updateCols = currentBatch.cols.filter((c) => !currentBatch.upsertKeys.includes(c) && !c.startsWith("_"));
299
+ if (batch.upsertKeys && batch.upsertKeys.length > 0) {
300
+ const batchKeys = batch.upsertKeys;
301
+ const updateCols = batch.cols.filter((c) => !batchKeys.includes(c) && !c.startsWith("_"));
289
302
  if (updateCols.length > 0) {
290
303
  const setClauses = updateCols.map((c) => `"${c}" = EXCLUDED."${c}"`);
291
- stmt += ` ON CONFLICT (${currentBatch.upsertKeys.map((k) => `"${k}"`).join(", ")}) DO UPDATE SET ${setClauses.join(", ")}`;
304
+ stmt += ` ON CONFLICT (${batchKeys.map((k) => `"${k}"`).join(", ")}) DO UPDATE SET ${setClauses.join(", ")}`;
292
305
  } else {
293
- stmt += ` ON CONFLICT (${currentBatch.upsertKeys.map((k) => `"${k}"`).join(", ")}) DO NOTHING`;
306
+ stmt += ` ON CONFLICT (${batchKeys.map((k) => `"${k}"`).join(", ")}) DO NOTHING`;
294
307
  }
295
308
  }
296
309
  statements.push(stmt);
@@ -311,8 +324,9 @@ class SubgraphContext {
311
324
  } else {
312
325
  flushInsertBatch();
313
326
  if (op.kind === "update") {
314
- const setEntries = Object.entries(op.set);
315
- setEntries.forEach(([k]) => validateColumnName(k));
327
+ const setEntries = Object.entries(op.set ?? {});
328
+ for (const [k] of setEntries)
329
+ validateColumnName(k);
316
330
  const setClauses = setEntries.map(([k, v]) => `"${k}" = ${escapeLiteral(v)}`);
317
331
  const { clause } = buildWhereClause(op.data);
318
332
  statements.push(`UPDATE ${qualifiedTable} SET ${setClauses.join(", ")} WHERE ${clause}`);
@@ -339,14 +353,15 @@ function escapeLiteral(value) {
339
353
  if (typeof value === "boolean")
340
354
  return value ? "TRUE" : "FALSE";
341
355
  if (typeof value === "object")
342
- return `'${JSON.stringify(value).replace(/'/g, "''")}'::jsonb`;
356
+ return `'${JSON.stringify(value, (_k, v) => typeof v === "bigint" ? v.toString() : v).replace(/'/g, "''")}'::jsonb`;
343
357
  return `'${String(value).replace(/'/g, "''")}'`;
344
358
  }
345
359
  function buildWhereClause(where) {
346
360
  const entries = Object.entries(where);
347
361
  if (entries.length === 0)
348
362
  return { clause: "TRUE", values: [] };
349
- entries.forEach(([k]) => validateColumnName(k));
363
+ for (const [k] of entries)
364
+ validateColumnName(k);
350
365
  const parts = entries.map(([k, v]) => `"${k}" = ${escapeLiteral(v)}`);
351
366
  return { clause: parts.join(" AND "), values: [] };
352
367
  }
@@ -1600,7 +1615,8 @@ function diffSchema(existing, incoming) {
1600
1615
  changed: [...incomingKeys].filter((k) => {
1601
1616
  if (!existingKeys.has(k))
1602
1617
  return false;
1603
- return JSON.stringify(existingCols[k]) !== JSON.stringify(incomingCols[k]);
1618
+ const sortedStringify = (o) => JSON.stringify(o, Object.keys(o).sort());
1619
+ return sortedStringify(existingCols[k]) !== sortedStringify(incomingCols[k]);
1604
1620
  })
1605
1621
  };
1606
1622
  }
@@ -1658,7 +1674,11 @@ async function deploySchema(db, def, handlerPath, opts) {
1658
1674
  if (existing.schema_hash === hash && !opts?.forceReindex) {
1659
1675
  const { updateSubgraphHandlerPath } = await import("@secondlayer/shared/db/queries/subgraphs");
1660
1676
  await updateSubgraphHandlerPath(db, def.name, handlerPath);
1661
- return { action: "unchanged", subgraphId: existing.id, version: existing.version };
1677
+ return {
1678
+ action: "unchanged",
1679
+ subgraphId: existing.id,
1680
+ version: existing.version
1681
+ };
1662
1682
  }
1663
1683
  if (existing.schema_hash === hash && opts?.forceReindex) {
1664
1684
  await sql3.raw(`DROP SCHEMA IF EXISTS "${schemaName}" CASCADE`).execute(db);
@@ -1683,10 +1703,17 @@ async function deploySchema(db, def, handlerPath, opts) {
1683
1703
  addedColumns: Object.fromEntries(Object.entries(diff.tables).filter(([, c]) => c.added.length > 0).map(([t, c]) => [t, c.added])),
1684
1704
  breakingChanges: reasons
1685
1705
  };
1686
- return { action: "reindexed", subgraphId: sg3.id, version: newVersion, diff: deployDiff2 };
1706
+ return {
1707
+ action: "reindexed",
1708
+ subgraphId: sg3.id,
1709
+ version: newVersion,
1710
+ diff: deployDiff2
1711
+ };
1687
1712
  }
1688
1713
  for (const tableName of diff.addedTables) {
1689
1714
  const tableDef = def.schema[tableName];
1715
+ if (!tableDef)
1716
+ continue;
1690
1717
  const qualifiedName = `${schemaName}.${tableName}`;
1691
1718
  const colDefs = [
1692
1719
  "_id BIGSERIAL PRIMARY KEY",
@@ -1696,7 +1723,10 @@ async function deploySchema(db, def, handlerPath, opts) {
1696
1723
  ];
1697
1724
  for (const [colName, col] of Object.entries(tableDef.columns)) {
1698
1725
  const nullable = col.nullable ? "" : " NOT NULL";
1699
- colDefs.push(`${colName} ${TYPE_MAP[col.type]}${nullable}`);
1726
+ const sqlType = TYPE_MAP[col.type];
1727
+ if (!sqlType)
1728
+ continue;
1729
+ colDefs.push(`${colName} ${sqlType}${nullable}`);
1700
1730
  }
1701
1731
  await sql3.raw(`CREATE TABLE IF NOT EXISTS ${qualifiedName} (
1702
1732
  ${colDefs.join(`,
@@ -1718,9 +1748,15 @@ async function deploySchema(db, def, handlerPath, opts) {
1718
1748
  continue;
1719
1749
  const qualifiedName = `${schemaName}.${tableName}`;
1720
1750
  const tableDef = def.schema[tableName];
1751
+ if (!tableDef)
1752
+ continue;
1721
1753
  for (const colName of colDiff.added) {
1722
1754
  const col = tableDef.columns[colName];
1755
+ if (!col)
1756
+ continue;
1723
1757
  const sqlType = TYPE_MAP[col.type];
1758
+ if (!sqlType)
1759
+ continue;
1724
1760
  const nullable = col.nullable ? "" : ` NOT NULL DEFAULT ${getDefault(col.type)}`;
1725
1761
  await sql3.raw(`ALTER TABLE ${qualifiedName} ADD COLUMN ${colName} ${sqlType}${nullable}`).execute(db);
1726
1762
  if (col.indexed) {
@@ -1743,7 +1779,12 @@ async function deploySchema(db, def, handlerPath, opts) {
1743
1779
  addedColumns: addedCols,
1744
1780
  breakingChanges: []
1745
1781
  };
1746
- return { action: "updated", subgraphId: sg2.id, version: newVersion, diff: deployDiff };
1782
+ return {
1783
+ action: "updated",
1784
+ subgraphId: sg2.id,
1785
+ version: newVersion,
1786
+ diff: deployDiff
1787
+ };
1747
1788
  }
1748
1789
  }
1749
1790
  for (const stmt of statements) {
@@ -1782,5 +1823,5 @@ export {
1782
1823
  backfillSubgraph
1783
1824
  };
1784
1825
 
1785
- //# debugId=212AA25CD1A71F2B64756E2164756E21
1826
+ //# debugId=BDEFBE84CC1D9E3564756E2164756E21
1786
1827
  //# sourceMappingURL=index.js.map