@inerrata-corporation/errata 2.0.22-dev.4020 → 2.0.22-dev.4054
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/consolidate-worker.mjs +285 -70
- package/errata.mjs +1921 -1110
- package/generalize-worker.mjs +234 -26
- package/package.json +1 -1
- package/pass-worker.mjs +440 -180
- package/resources/context-plugin/.codex-plugin/plugin.json +1 -1
- package/resources/context-plugin/SHA256SUMS +1 -1
package/generalize-worker.mjs
CHANGED
|
@@ -1235,10 +1235,10 @@ function mergeDefs(...defs) {
|
|
|
1235
1235
|
function cloneDef(schema) {
|
|
1236
1236
|
return mergeDefs(schema._zod.def);
|
|
1237
1237
|
}
|
|
1238
|
-
function getElementAtPath(obj,
|
|
1239
|
-
if (!
|
|
1238
|
+
function getElementAtPath(obj, path2) {
|
|
1239
|
+
if (!path2)
|
|
1240
1240
|
return obj;
|
|
1241
|
-
return
|
|
1241
|
+
return path2.reduce((acc, key) => acc?.[key], obj);
|
|
1242
1242
|
}
|
|
1243
1243
|
function promiseAllObject(promisesObj) {
|
|
1244
1244
|
const keys = Object.keys(promisesObj);
|
|
@@ -1621,11 +1621,11 @@ function aborted(x, startIndex = 0) {
|
|
|
1621
1621
|
}
|
|
1622
1622
|
return false;
|
|
1623
1623
|
}
|
|
1624
|
-
function prefixIssues(
|
|
1624
|
+
function prefixIssues(path2, issues) {
|
|
1625
1625
|
return issues.map((iss) => {
|
|
1626
1626
|
var _a2;
|
|
1627
1627
|
(_a2 = iss).path ?? (_a2.path = []);
|
|
1628
|
-
iss.path.unshift(
|
|
1628
|
+
iss.path.unshift(path2);
|
|
1629
1629
|
return iss;
|
|
1630
1630
|
});
|
|
1631
1631
|
}
|
|
@@ -1808,7 +1808,7 @@ function formatError(error48, mapper = (issue2) => issue2.message) {
|
|
|
1808
1808
|
}
|
|
1809
1809
|
function treeifyError(error48, mapper = (issue2) => issue2.message) {
|
|
1810
1810
|
const result = { errors: [] };
|
|
1811
|
-
const processError = (error49,
|
|
1811
|
+
const processError = (error49, path2 = []) => {
|
|
1812
1812
|
var _a2, _b;
|
|
1813
1813
|
for (const issue2 of error49.issues) {
|
|
1814
1814
|
if (issue2.code === "invalid_union" && issue2.errors.length) {
|
|
@@ -1818,7 +1818,7 @@ function treeifyError(error48, mapper = (issue2) => issue2.message) {
|
|
|
1818
1818
|
} else if (issue2.code === "invalid_element") {
|
|
1819
1819
|
processError({ issues: issue2.issues }, issue2.path);
|
|
1820
1820
|
} else {
|
|
1821
|
-
const fullpath = [...
|
|
1821
|
+
const fullpath = [...path2, ...issue2.path];
|
|
1822
1822
|
if (fullpath.length === 0) {
|
|
1823
1823
|
result.errors.push(mapper(issue2));
|
|
1824
1824
|
continue;
|
|
@@ -1850,8 +1850,8 @@ function treeifyError(error48, mapper = (issue2) => issue2.message) {
|
|
|
1850
1850
|
}
|
|
1851
1851
|
function toDotPath(_path) {
|
|
1852
1852
|
const segs = [];
|
|
1853
|
-
const
|
|
1854
|
-
for (const seg of
|
|
1853
|
+
const path2 = _path.map((seg) => typeof seg === "object" ? seg.key : seg);
|
|
1854
|
+
for (const seg of path2) {
|
|
1855
1855
|
if (typeof seg === "number")
|
|
1856
1856
|
segs.push(`[${seg}]`);
|
|
1857
1857
|
else if (typeof seg === "symbol")
|
|
@@ -13828,13 +13828,13 @@ function resolveRef(ref, ctx) {
|
|
|
13828
13828
|
if (!ref.startsWith("#")) {
|
|
13829
13829
|
throw new Error("External $ref is not supported, only local refs (#/...) are allowed");
|
|
13830
13830
|
}
|
|
13831
|
-
const
|
|
13832
|
-
if (
|
|
13831
|
+
const path2 = ref.slice(1).split("/").filter(Boolean);
|
|
13832
|
+
if (path2.length === 0) {
|
|
13833
13833
|
return ctx.rootSchema;
|
|
13834
13834
|
}
|
|
13835
13835
|
const defsKey = ctx.version === "draft-2020-12" ? "$defs" : "definitions";
|
|
13836
|
-
if (
|
|
13837
|
-
const key =
|
|
13836
|
+
if (path2[0] === defsKey) {
|
|
13837
|
+
const key = path2[1];
|
|
13838
13838
|
if (!key || !ctx.defs[key]) {
|
|
13839
13839
|
throw new Error(`Reference not found: ${ref}`);
|
|
13840
13840
|
}
|
|
@@ -14773,13 +14773,13 @@ function loadNodeSqlite() {
|
|
|
14773
14773
|
}
|
|
14774
14774
|
}
|
|
14775
14775
|
var DatabaseSync = loadNodeSqlite().DatabaseSync;
|
|
14776
|
-
function openDatabase(
|
|
14777
|
-
const db = opts ? new DatabaseSync(
|
|
14776
|
+
function openDatabase(path2, opts) {
|
|
14777
|
+
const db = opts ? new DatabaseSync(path2, opts) : new DatabaseSync(path2);
|
|
14778
14778
|
try {
|
|
14779
14779
|
db.exec("PRAGMA foreign_keys = ON");
|
|
14780
14780
|
} catch {
|
|
14781
14781
|
}
|
|
14782
|
-
if (
|
|
14782
|
+
if (path2 !== ":memory:" && !opts?.readOnly) {
|
|
14783
14783
|
try {
|
|
14784
14784
|
db.exec("PRAGMA journal_mode = WAL");
|
|
14785
14785
|
db.exec("PRAGMA synchronous = NORMAL");
|
|
@@ -15093,6 +15093,38 @@ function installHistoryAttrSlim(db) {
|
|
|
15093
15093
|
db.prepare("INSERT INTO store_meta(key,value) VALUES (?,?)").run(HISTORY_ATTR_SLIM_KEY, "done");
|
|
15094
15094
|
}
|
|
15095
15095
|
|
|
15096
|
+
// ../../packages/local-graph/src/text-index.ts
|
|
15097
|
+
var TEXT_INDEX_KEY = "text-index-trigram-1";
|
|
15098
|
+
var TEXT_INDEX_MIN_TERM = 3;
|
|
15099
|
+
function installTextIndex(db) {
|
|
15100
|
+
if (db.prepare("SELECT value FROM store_meta WHERE key = ?").get(TEXT_INDEX_KEY)) return;
|
|
15101
|
+
try {
|
|
15102
|
+
db.exec(`CREATE VIRTUAL TABLE temp.fts5_probe USING fts5(x, tokenize='trigram'); DROP TABLE temp.fts5_probe`);
|
|
15103
|
+
} catch {
|
|
15104
|
+
db.prepare("INSERT INTO store_meta(key,value) VALUES (?,?)").run(TEXT_INDEX_KEY, "unavailable");
|
|
15105
|
+
return;
|
|
15106
|
+
}
|
|
15107
|
+
db.transaction(() => {
|
|
15108
|
+
db.exec(`CREATE VIRTUAL TABLE IF NOT EXISTS nodes_text
|
|
15109
|
+
USING fts5(description, content='nodes', content_rowid='rowid', tokenize='trigram')`);
|
|
15110
|
+
db.exec(`CREATE TRIGGER IF NOT EXISTS nodes_text_insert AFTER INSERT ON nodes WHEN NEW.valid_to IS NULL
|
|
15111
|
+
BEGIN INSERT INTO nodes_text(rowid, description) VALUES (NEW.rowid, NEW.description); END;`);
|
|
15112
|
+
db.exec(`CREATE TRIGGER IF NOT EXISTS nodes_text_update_out AFTER UPDATE OF description, valid_to ON nodes
|
|
15113
|
+
WHEN OLD.valid_to IS NULL
|
|
15114
|
+
BEGIN INSERT INTO nodes_text(nodes_text, rowid, description) VALUES ('delete', OLD.rowid, OLD.description); END;`);
|
|
15115
|
+
db.exec(`CREATE TRIGGER IF NOT EXISTS nodes_text_update_in AFTER UPDATE OF description, valid_to ON nodes
|
|
15116
|
+
WHEN NEW.valid_to IS NULL
|
|
15117
|
+
BEGIN INSERT INTO nodes_text(rowid, description) VALUES (NEW.rowid, NEW.description); END;`);
|
|
15118
|
+
db.exec(`CREATE TRIGGER IF NOT EXISTS nodes_text_delete AFTER DELETE ON nodes WHEN OLD.valid_to IS NULL
|
|
15119
|
+
BEGIN INSERT INTO nodes_text(nodes_text, rowid, description) VALUES ('delete', OLD.rowid, OLD.description); END;`);
|
|
15120
|
+
db.exec(`INSERT INTO nodes_text(rowid, description) SELECT rowid, description FROM nodes WHERE valid_to IS NULL`);
|
|
15121
|
+
db.prepare("INSERT INTO store_meta(key,value) VALUES (?,?)").run(TEXT_INDEX_KEY, "installed");
|
|
15122
|
+
});
|
|
15123
|
+
}
|
|
15124
|
+
function textIndexReady(db) {
|
|
15125
|
+
return db.prepare("SELECT value FROM store_meta WHERE key = ?").get(TEXT_INDEX_KEY)?.["value"] === "installed";
|
|
15126
|
+
}
|
|
15127
|
+
|
|
15096
15128
|
// ../../packages/math/src/relevance.ts
|
|
15097
15129
|
function pageRankScale(ranks) {
|
|
15098
15130
|
const positive = [...ranks].filter((r) => Number.isFinite(r) && r > 0).sort((a, b) => a - b);
|
|
@@ -15103,6 +15135,140 @@ function pageRankScale(ranks) {
|
|
|
15103
15135
|
var DEMAND_HOT = Math.log1p(10);
|
|
15104
15136
|
var DEMAND_WARM = Math.log1p(5);
|
|
15105
15137
|
|
|
15138
|
+
// ../../packages/local-graph/src/node-select.ts
|
|
15139
|
+
var EMBEDDING_DIM_SQL = "(CASE WHEN length(embedding_blob) >= 4 THEN length(embedding_blob) / 4 ELSE COALESCE(json_array_length(embedding_json), 0) END)";
|
|
15140
|
+
var KEY = /^[A-Za-z_][A-Za-z0-9_]*(\.[A-Za-z_][A-Za-z0-9_]*)*$/;
|
|
15141
|
+
var COLUMNS = /* @__PURE__ */ new Set([
|
|
15142
|
+
"created_at",
|
|
15143
|
+
"last_updated_at",
|
|
15144
|
+
"page_rank",
|
|
15145
|
+
"created_at_seq",
|
|
15146
|
+
"last_reinforced_at_seq",
|
|
15147
|
+
"cumulative_hits",
|
|
15148
|
+
"extraction_confidence"
|
|
15149
|
+
]);
|
|
15150
|
+
function path(key) {
|
|
15151
|
+
if (!KEY.test(key)) throw new Error(`selectNodes: bad attr key ${key}`);
|
|
15152
|
+
return `'$.${key}'`;
|
|
15153
|
+
}
|
|
15154
|
+
function column(c) {
|
|
15155
|
+
if (!COLUMNS.has(c)) throw new Error(`selectNodes: bad column ${c}`);
|
|
15156
|
+
return c;
|
|
15157
|
+
}
|
|
15158
|
+
function compileNodeWhere(q) {
|
|
15159
|
+
if (q.labels.length === 0) throw new Error("selectNodes: no labels");
|
|
15160
|
+
const params = [...q.labels];
|
|
15161
|
+
const conds = [`label IN (${q.labels.map(() => "?").join(", ")})`];
|
|
15162
|
+
if (!q.includeClosed) conds.push("valid_to IS NULL");
|
|
15163
|
+
for (const w of q.where ?? []) {
|
|
15164
|
+
if ("embedding" in w) {
|
|
15165
|
+
conds.push(`${EMBEDDING_DIM_SQL} ${w.embedding === "present" ? ">" : "="} 0`);
|
|
15166
|
+
} else if ("idPrefix" in w) {
|
|
15167
|
+
conds.push("substr(id, 1, ?) = ?");
|
|
15168
|
+
params.push(w.idPrefix.length, w.idPrefix);
|
|
15169
|
+
} else if ("descriptionIn" in w) {
|
|
15170
|
+
if (w.descriptionIn.length === 0) conds.push("0");
|
|
15171
|
+
else {
|
|
15172
|
+
conds.push(`description IN (${w.descriptionIn.map(() => "?").join(", ")})`);
|
|
15173
|
+
params.push(...w.descriptionIn);
|
|
15174
|
+
}
|
|
15175
|
+
} else if ("column" in w) {
|
|
15176
|
+
const c = column(w.column);
|
|
15177
|
+
for (const [op, sym] of [["gte", ">="], ["gt", ">"], ["lte", "<="], ["lt", "<"]]) {
|
|
15178
|
+
const v = w[op];
|
|
15179
|
+
if (v !== void 0) {
|
|
15180
|
+
conds.push(`${c} ${sym} ?`);
|
|
15181
|
+
params.push(v);
|
|
15182
|
+
}
|
|
15183
|
+
}
|
|
15184
|
+
} else {
|
|
15185
|
+
const p = path(w.attr);
|
|
15186
|
+
if ("absent" in w) conds.push(`json_type(attrs_json, ${p}) IS NULL`);
|
|
15187
|
+
else if ("present" in w) conds.push(`json_type(attrs_json, ${p}) IS NOT NULL`);
|
|
15188
|
+
else if ("nullish" in w) conds.push(`json_extract(attrs_json, ${p}) IS NULL`);
|
|
15189
|
+
else if ("notNullish" in w) conds.push(`json_extract(attrs_json, ${p}) IS NOT NULL`);
|
|
15190
|
+
else if ("eq" in w || "ne" in w) {
|
|
15191
|
+
const v = "eq" in w ? w.eq : w.ne;
|
|
15192
|
+
const neg = "ne" in w;
|
|
15193
|
+
if (typeof v === "boolean") {
|
|
15194
|
+
conds.push(`json_type(attrs_json, ${p}) ${neg ? "IS NOT" : "="} ?`);
|
|
15195
|
+
params.push(v ? "true" : "false");
|
|
15196
|
+
} else {
|
|
15197
|
+
conds.push(neg ? `json_extract(attrs_json, ${p}) IS NOT ?` : `json_extract(attrs_json, ${p}) = ?`);
|
|
15198
|
+
params.push(v);
|
|
15199
|
+
}
|
|
15200
|
+
}
|
|
15201
|
+
}
|
|
15202
|
+
}
|
|
15203
|
+
return { where: conds.join(" AND "), params };
|
|
15204
|
+
}
|
|
15205
|
+
function attrValueSql(p) {
|
|
15206
|
+
return `CASE json_type(attrs_json, ${p}) WHEN 'integer' THEN CAST(json_extract(attrs_json, ${p}) AS REAL) ELSE json_extract(attrs_json, ${p}) END`;
|
|
15207
|
+
}
|
|
15208
|
+
function compileNodeSelect(q) {
|
|
15209
|
+
const { where, params } = compileNodeWhere(q);
|
|
15210
|
+
const attrs = q.attrs ?? [];
|
|
15211
|
+
const attrCols = attrs.map((k, i) => `, ${attrValueSql(path(k))} AS a${i}, json_type(attrs_json, ${path(k)}) AS t${i}`).join("");
|
|
15212
|
+
let order;
|
|
15213
|
+
if (q.orderBy && "column" in q.orderBy) {
|
|
15214
|
+
order = `${column(q.orderBy.column)} ${q.orderBy.desc ? "DESC" : "ASC"}, rowid`;
|
|
15215
|
+
} else if (q.orderBy) {
|
|
15216
|
+
const p = path(q.orderBy.attr);
|
|
15217
|
+
order = `json_extract(attrs_json, ${p}) IS NULL, json_extract(attrs_json, ${p}) ${q.orderBy.desc ? "DESC" : "ASC"}, rowid`;
|
|
15218
|
+
} else if (q.labels.length > 1) {
|
|
15219
|
+
order = `CASE label ${q.labels.map((_, i) => `WHEN ? THEN ${i}`).join(" ")} END, rowid`;
|
|
15220
|
+
} else {
|
|
15221
|
+
order = "rowid";
|
|
15222
|
+
}
|
|
15223
|
+
const orderParams = !q.orderBy && q.labels.length > 1 ? [...q.labels] : [];
|
|
15224
|
+
const limit = q.limit !== void 0 ? ` LIMIT ${Math.max(0, Math.floor(q.limit))}` : "";
|
|
15225
|
+
const sql = `SELECT id, label, description, created_at, last_updated_at, page_rank, cumulative_hits, extraction_confidence, extraction_source, community, created_at_seq, last_reinforced_at_seq, valid_to, ${EMBEDDING_DIM_SQL} AS embedding_dim${q.withEmbedding ? ", embedding_blob, embedding_json" : ""}${attrCols} FROM nodes WHERE ${where} ORDER BY ${order}${limit}`;
|
|
15226
|
+
return { sql, params: [...params, ...orderParams] };
|
|
15227
|
+
}
|
|
15228
|
+
function decodeAttr(value, type) {
|
|
15229
|
+
switch (type) {
|
|
15230
|
+
case null:
|
|
15231
|
+
case void 0:
|
|
15232
|
+
return void 0;
|
|
15233
|
+
case "true":
|
|
15234
|
+
return true;
|
|
15235
|
+
case "false":
|
|
15236
|
+
return false;
|
|
15237
|
+
case "null":
|
|
15238
|
+
return null;
|
|
15239
|
+
case "object":
|
|
15240
|
+
case "array":
|
|
15241
|
+
return typeof value === "string" ? JSON.parse(value) : value;
|
|
15242
|
+
default:
|
|
15243
|
+
return value;
|
|
15244
|
+
}
|
|
15245
|
+
}
|
|
15246
|
+
function decodeSelectedRow(r, attrs, decodeVector) {
|
|
15247
|
+
const out = {};
|
|
15248
|
+
attrs.forEach((k, i) => {
|
|
15249
|
+
const v = decodeAttr(r[`a${i}`], r[`t${i}`]);
|
|
15250
|
+
if (v !== void 0) out[k] = v;
|
|
15251
|
+
});
|
|
15252
|
+
return {
|
|
15253
|
+
id: r["id"],
|
|
15254
|
+
label: r["label"],
|
|
15255
|
+
description: r["description"] ?? "",
|
|
15256
|
+
createdAt: r["created_at"],
|
|
15257
|
+
lastUpdatedAt: r["last_updated_at"],
|
|
15258
|
+
pageRank: r["page_rank"],
|
|
15259
|
+
cumulativeHits: r["cumulative_hits"],
|
|
15260
|
+
extractionConfidence: r["extraction_confidence"],
|
|
15261
|
+
extractionSource: r["extraction_source"],
|
|
15262
|
+
community: r["community"] ?? null,
|
|
15263
|
+
...r["created_at_seq"] != null ? { createdAtSeq: r["created_at_seq"] } : {},
|
|
15264
|
+
...r["last_reinforced_at_seq"] != null ? { lastReinforcedAtSeq: r["last_reinforced_at_seq"] } : {},
|
|
15265
|
+
validTo: r["valid_to"] ?? null,
|
|
15266
|
+
embeddingDim: Number(r["embedding_dim"] ?? 0),
|
|
15267
|
+
...decodeVector ? { embedding: decodeVector(r["embedding_blob"], r["embedding_json"] ?? "[]") } : {},
|
|
15268
|
+
attrs: out
|
|
15269
|
+
};
|
|
15270
|
+
}
|
|
15271
|
+
|
|
15106
15272
|
// ../../packages/local-graph/src/store.ts
|
|
15107
15273
|
var PAGE_RANK_SCALE_KEY = "pageRankScale.p95.v1";
|
|
15108
15274
|
var TEXT_SEARCH_COLUMNS = `id, label, description, page_rank,
|
|
@@ -15291,6 +15457,11 @@ CREATE INDEX IF NOT EXISTS nodes_cloud_node_id ON nodes(json_extract(attrs_json,
|
|
|
15291
15457
|
-- Solution's and Problem's attrs per call. Not partial: the Problem pull reads
|
|
15292
15458
|
-- closed versions too.
|
|
15293
15459
|
CREATE INDEX IF NOT EXISTS nodes_enrichment_pending ON nodes(json_extract(attrs_json, '$.enrichmentPending'));
|
|
15460
|
+
-- Revisit flags, any label, any version: listNeedsRevisit's as-of read runs on
|
|
15461
|
+
-- every context render and otherwise json-checks every row (10.3 s on a 324k-row
|
|
15462
|
+
-- store, to return zero flags). The predicate must stay textually identical to
|
|
15463
|
+
-- nodesAsOfWhereTrue's or the planner will not use it.
|
|
15464
|
+
CREATE INDEX IF NOT EXISTS nodes_revisit_true ON nodes(valid_from) WHERE json_type(attrs_json, '$.revisit') = 'true';
|
|
15294
15465
|
`;
|
|
15295
15466
|
function encodeEmbedding(emb) {
|
|
15296
15467
|
if (!emb || emb.length === 0) return null;
|
|
@@ -15391,6 +15562,7 @@ var SqliteGraphStore = class {
|
|
|
15391
15562
|
installEditPlaceholderRetirement(this.db);
|
|
15392
15563
|
installCloudAttrCompaction(this.db);
|
|
15393
15564
|
installHistoryAttrSlim(this.db);
|
|
15565
|
+
installTextIndex(this.db);
|
|
15394
15566
|
if (!this.db.prepare("SELECT value FROM store_meta WHERE key = ?").get(SESSION_REPAIR_KEY)) {
|
|
15395
15567
|
this.db.transaction(() => {
|
|
15396
15568
|
this.repairSessionAliases();
|
|
@@ -15768,8 +15940,8 @@ var SqliteGraphStore = class {
|
|
|
15768
15940
|
setLandmark(id, isLandmark) {
|
|
15769
15941
|
this.stmts.setLandmark.run({ id, v: isLandmark ? 1 : 0 });
|
|
15770
15942
|
}
|
|
15771
|
-
setLocalCommunity(id, community,
|
|
15772
|
-
this.stmts.setLocalCommunity.run({ id, v: community, col:
|
|
15943
|
+
setLocalCommunity(id, community, column2) {
|
|
15944
|
+
this.stmts.setLocalCommunity.run({ id, v: community, col: column2 ? 1 : 0 });
|
|
15773
15945
|
}
|
|
15774
15946
|
fieldStmts = /* @__PURE__ */ new Map();
|
|
15775
15947
|
findNodeFieldsByLabel(label, attrKeys) {
|
|
@@ -15777,7 +15949,7 @@ var SqliteGraphStore = class {
|
|
|
15777
15949
|
const cacheKey = attrKeys.join(",");
|
|
15778
15950
|
let stmt = this.fieldStmts.get(cacheKey);
|
|
15779
15951
|
if (!stmt) {
|
|
15780
|
-
const cols = attrKeys.map((k, i) => `,
|
|
15952
|
+
const cols = attrKeys.map((k, i) => `, ${attrValueSql(`'$.${k}'`)} AS a${i}, json_type(attrs_json, '$.${k}') AS t${i}`).join("");
|
|
15781
15953
|
stmt = this.db.prepare(
|
|
15782
15954
|
`SELECT id, description, community, extraction_confidence${cols} FROM nodes WHERE label = ? AND valid_to IS NULL`
|
|
15783
15955
|
);
|
|
@@ -15786,8 +15958,8 @@ var SqliteGraphStore = class {
|
|
|
15786
15958
|
return stmt.all(label).map((r) => {
|
|
15787
15959
|
const attrs = {};
|
|
15788
15960
|
attrKeys.forEach((k, i) => {
|
|
15789
|
-
const v = r[`a${i}`];
|
|
15790
|
-
if (v !==
|
|
15961
|
+
const v = decodeAttr(r[`a${i}`], r[`t${i}`]);
|
|
15962
|
+
if (v !== void 0) attrs[k] = v;
|
|
15791
15963
|
});
|
|
15792
15964
|
return {
|
|
15793
15965
|
id: r["id"],
|
|
@@ -15798,6 +15970,15 @@ var SqliteGraphStore = class {
|
|
|
15798
15970
|
};
|
|
15799
15971
|
});
|
|
15800
15972
|
}
|
|
15973
|
+
selectNodes(q) {
|
|
15974
|
+
const { sql, params } = compileNodeSelect(q);
|
|
15975
|
+
const rows = this.db.prepare(sql).all(...params);
|
|
15976
|
+
return rows.map((r) => decodeSelectedRow(r, q.attrs ?? [], q.withEmbedding ? decodeEmbedding : void 0));
|
|
15977
|
+
}
|
|
15978
|
+
countNodes(q) {
|
|
15979
|
+
const { where, params } = compileNodeWhere(q);
|
|
15980
|
+
return Number(this.db.prepare(`SELECT COUNT(*) AS n FROM nodes WHERE ${where}`).get(...params).n);
|
|
15981
|
+
}
|
|
15801
15982
|
setCommunity(id, community) {
|
|
15802
15983
|
this.stmts.setCommunity.run({ id, v: community });
|
|
15803
15984
|
}
|
|
@@ -16045,6 +16226,20 @@ var SqliteGraphStore = class {
|
|
|
16045
16226
|
}
|
|
16046
16227
|
searchTextCandidates(terms) {
|
|
16047
16228
|
if (terms.length === 0) return [];
|
|
16229
|
+
const indexed = terms.filter((t) => t.length >= TEXT_INDEX_MIN_TERM);
|
|
16230
|
+
if (indexed.length > 0 && textIndexReady(this.db)) {
|
|
16231
|
+
const short = terms.filter((t) => t.length < TEXT_INDEX_MIN_TERM).map((t) => t.toLowerCase());
|
|
16232
|
+
const rows2 = this.db.prepare(`WITH hits AS MATERIALIZED (
|
|
16233
|
+
SELECT t.rowid AS rid, COUNT(*) AS matched FROM json_each(:terms) q, nodes_text t
|
|
16234
|
+
WHERE t.description LIKE '%' || q.value || '%' GROUP BY t.rowid
|
|
16235
|
+
) SELECT ${TEXT_SEARCH_COLUMNS}, hits.matched FROM hits JOIN nodes ON nodes.rowid = hits.rid
|
|
16236
|
+
WHERE nodes.valid_to IS NULL ORDER BY page_rank DESC, last_updated_at DESC`).all({ terms: JSON.stringify(indexed) });
|
|
16237
|
+
return rows2.map((row) => {
|
|
16238
|
+
const text = row.description.toLowerCase();
|
|
16239
|
+
const extra = short.filter((t) => text.includes(t)).length;
|
|
16240
|
+
return { node: textSearchNode(row), matched: row.matched + extra };
|
|
16241
|
+
});
|
|
16242
|
+
}
|
|
16048
16243
|
const rows = this.db.prepare(`WITH matches AS MATERIALIZED (
|
|
16049
16244
|
SELECT n.id, COUNT(*) AS matched FROM nodes n INDEXED BY nodes_live_description, json_each(:terms) t
|
|
16050
16245
|
WHERE n.valid_to IS NULL AND n.description LIKE '%' || t.value || '%'
|
|
@@ -16053,6 +16248,18 @@ var SqliteGraphStore = class {
|
|
|
16053
16248
|
JOIN matches USING (id) ORDER BY page_rank DESC, last_updated_at DESC`).all({ terms: JSON.stringify(terms) });
|
|
16054
16249
|
return rows.map((row) => ({ node: textSearchNode(row), matched: row.matched }));
|
|
16055
16250
|
}
|
|
16251
|
+
commentAnchors(commentIds) {
|
|
16252
|
+
const out = /* @__PURE__ */ new Map();
|
|
16253
|
+
if (commentIds.length === 0) return out;
|
|
16254
|
+
const rows = this.db.prepare(`WITH a AS MATERIALIZED (
|
|
16255
|
+
SELECT q.value AS cid, COALESCE(
|
|
16256
|
+
(SELECT to_id FROM edges WHERE from_id = q.value AND type IN ('EXPLAINS', 'ANNOTATES') AND valid_to IS NULL LIMIT 1),
|
|
16257
|
+
(SELECT from_id FROM edges WHERE to_id = q.value AND type = 'DOCUMENTED_BY' AND valid_to IS NULL LIMIT 1)
|
|
16258
|
+
) AS aid FROM json_each(:ids) q
|
|
16259
|
+
) SELECT a.cid AS cid, ${TEXT_SEARCH_COLUMNS} FROM a JOIN nodes ON nodes.id = a.aid AND nodes.valid_to IS NULL`).all({ ids: JSON.stringify(commentIds) });
|
|
16260
|
+
for (const row of rows) out.set(row.cid, textSearchNode(row));
|
|
16261
|
+
return out;
|
|
16262
|
+
}
|
|
16056
16263
|
getTextSearchNode(id) {
|
|
16057
16264
|
const row = this.db.prepare(`SELECT ${TEXT_SEARCH_COLUMNS} FROM nodes WHERE id = ? AND valid_to IS NULL`).get(id);
|
|
16058
16265
|
return row ? textSearchNode(row) : null;
|
|
@@ -16448,7 +16655,8 @@ var SqliteGraphStore = class {
|
|
|
16448
16655
|
if (!/^[A-Za-z_][A-Za-z0-9_]*$/.test(attr)) throw new Error(`nodesAsOfWhereTrue: bad attr ${JSON.stringify(attr)}`);
|
|
16449
16656
|
const rows = this.db.prepare(
|
|
16450
16657
|
`SELECT * FROM nodes WHERE valid_from <= :t AND (valid_to IS NULL OR valid_to > :t)
|
|
16451
|
-
AND json_type(attrs_json, '$.${attr}') = 'true'
|
|
16658
|
+
AND json_type(attrs_json, '$.${attr}') = 'true'
|
|
16659
|
+
ORDER BY rowid`
|
|
16452
16660
|
).all({ t });
|
|
16453
16661
|
return rows.map(rowToNode);
|
|
16454
16662
|
}
|
|
@@ -17409,11 +17617,11 @@ function generalizeSymbols(text, lexicon, level = 1, fileLexicon) {
|
|
|
17409
17617
|
|
|
17410
17618
|
// src/generalize-worker.ts
|
|
17411
17619
|
var stores = /* @__PURE__ */ new Map();
|
|
17412
|
-
function storeAt(
|
|
17413
|
-
let s = stores.get(
|
|
17620
|
+
function storeAt(path2) {
|
|
17621
|
+
let s = stores.get(path2);
|
|
17414
17622
|
if (!s) {
|
|
17415
|
-
s = openGraphStore({ path });
|
|
17416
|
-
stores.set(
|
|
17623
|
+
s = openGraphStore({ path: path2 });
|
|
17624
|
+
stores.set(path2, s);
|
|
17417
17625
|
}
|
|
17418
17626
|
return s;
|
|
17419
17627
|
}
|