ygl-trees 0.76.0 → 0.77.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/CHANGELOG.md +12 -0
- package/README.md +1 -1
- package/dist/apps/cli/src/bin.js +15 -0
- package/dist/bundle/bin.cjs +258 -297
- package/dist/bundle/text-Bce0wNAD.cjs +172 -0
- package/dist/packages/core/database/src/plugin.js +32 -0
- package/dist/packages/knowledge/skills/src/skill-cmds.js +38 -5
- package/dist/packages/ops/tools/src/plugins.js +31 -2
- package/docs/plugin-authoring.md +19 -0
- package/llms.txt +1 -1
- package/package.json +4 -4
package/dist/bundle/bin.cjs
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
|
|
3
3
|
const require_rolldown_runtime = require("./rolldown-runtime-C96Ew50Q.cjs");
|
|
4
|
+
const require_text = require("./text-Bce0wNAD.cjs");
|
|
4
5
|
let node_os = require("node:os");
|
|
5
6
|
node_os = require_rolldown_runtime.__toESM(node_os);
|
|
6
7
|
let node_path = require("node:path");
|
|
@@ -12,130 +13,13 @@ let node_crypto = require("node:crypto");
|
|
|
12
13
|
let _deepseek_ai_cordis = require("@deepseek-ai/cordis");
|
|
13
14
|
require("reflect-metadata");
|
|
14
15
|
let typeorm = require("typeorm");
|
|
16
|
+
let node_events = require("node:events");
|
|
15
17
|
let _deepseek_ai_cordis_plugin_timer = require("@deepseek-ai/cordis-plugin-timer");
|
|
16
18
|
_deepseek_ai_cordis_plugin_timer = require_rolldown_runtime.__toESM(_deepseek_ai_cordis_plugin_timer);
|
|
17
19
|
let node_child_process = require("node:child_process");
|
|
18
20
|
let _deepseek_ai_dsh_atomic_write = require("@deepseek-ai/dsh-atomic-write");
|
|
19
|
-
let node_events = require("node:events");
|
|
20
21
|
let _deepseek_ai_schemastery = require("@deepseek-ai/schemastery");
|
|
21
22
|
_deepseek_ai_schemastery = require_rolldown_runtime.__toESM(_deepseek_ai_schemastery);
|
|
22
|
-
//#region packages/core/text/src/text.ts
|
|
23
|
-
var text_exports = /* @__PURE__ */ require_rolldown_runtime.__exportAll({
|
|
24
|
-
clip: () => clip,
|
|
25
|
-
contentHash: () => contentHash,
|
|
26
|
-
ngram: () => ngram,
|
|
27
|
-
nowIso: () => nowIso,
|
|
28
|
-
parseFrontmatter: () => parseFrontmatter,
|
|
29
|
-
sha1: () => sha1,
|
|
30
|
-
shortId: () => shortId,
|
|
31
|
-
slug: () => slug,
|
|
32
|
-
splitTags: () => splitTags,
|
|
33
|
-
stampId: () => stampId
|
|
34
|
-
});
|
|
35
|
-
function nowIso() {
|
|
36
|
-
const d = /* @__PURE__ */ new Date();
|
|
37
|
-
const p = (n) => String(n).padStart(2, "0");
|
|
38
|
-
return `${d.getFullYear()}-${p(d.getMonth() + 1)}-${p(d.getDate())} ${p(d.getHours())}:${p(d.getMinutes())}:${p(d.getSeconds())}`;
|
|
39
|
-
}
|
|
40
|
-
function stampId() {
|
|
41
|
-
const d = /* @__PURE__ */ new Date();
|
|
42
|
-
const p = (n) => String(n).padStart(2, "0");
|
|
43
|
-
return `${d.getFullYear()}${p(d.getMonth() + 1)}${p(d.getDate())}-${p(d.getHours())}${p(d.getMinutes())}${p(d.getSeconds())}`;
|
|
44
|
-
}
|
|
45
|
-
function slug(text, limit = 40) {
|
|
46
|
-
const s = (text || "").trim().toLowerCase().replace(new RegExp(`[^\\w${CJK}]+`, "gu"), "-").replace(/^-+|-+$/g, "");
|
|
47
|
-
if (s.length <= limit) return s || "item";
|
|
48
|
-
return s.slice(0, limit).replace(/-+$/, "") || "item";
|
|
49
|
-
}
|
|
50
|
-
/**
|
|
51
|
-
* Tokenize mixed Chinese/English text for SQLite FTS5.
|
|
52
|
-
*
|
|
53
|
-
* FTS5's default unicode61 tokenizer treats a whole CJK sentence as one token,
|
|
54
|
-
* which makes Chinese search degrade to exact match. We expand CJK runs into
|
|
55
|
-
* character bigrams and keep latin words intact.
|
|
56
|
-
*/
|
|
57
|
-
function ngram(text) {
|
|
58
|
-
const src = (text || "").normalize("NFKC").toLowerCase();
|
|
59
|
-
const out = [];
|
|
60
|
-
const segs = src.match(CJK_RUN_RE) || [];
|
|
61
|
-
for (const seg of segs) if (CJK_ONLY_RE.test(seg)) {
|
|
62
|
-
if (seg.length === 1) out.push(seg);
|
|
63
|
-
else for (let i = 0; i < seg.length - 1; i++) out.push(seg.slice(i, i + 2));
|
|
64
|
-
} else {
|
|
65
|
-
const w = seg.replace(/^[^\w]+|[^\w]+$/gu, "");
|
|
66
|
-
if (w) out.push(w);
|
|
67
|
-
}
|
|
68
|
-
return out.join(" ");
|
|
69
|
-
}
|
|
70
|
-
function sha1(text) {
|
|
71
|
-
return require("node:crypto").createHash("sha1").update(text || "").digest("hex");
|
|
72
|
-
}
|
|
73
|
-
/** Content hash for idempotent writes (single source: store writes and the
|
|
74
|
-
* TypeORM write service must produce identical hashes); --force salts it
|
|
75
|
-
* so a duplicate row is explicitly distinct (queryable via `db dups`). */
|
|
76
|
-
function contentHash(content, force) {
|
|
77
|
-
return sha1(content) + (force ? `#f${Date.now()}${Math.random()}` : "");
|
|
78
|
-
}
|
|
79
|
-
function shortId(parts, n = 8) {
|
|
80
|
-
return sha1(parts.join("|") + Date.now() + Math.random()).slice(0, n);
|
|
81
|
-
}
|
|
82
|
-
/** Truncate for table display, collapsing newlines. */
|
|
83
|
-
function clip(text, n = 40) {
|
|
84
|
-
const one = (text || "").replace(/\s+/g, " ").trim();
|
|
85
|
-
return one.length <= n ? one : one.slice(0, Math.max(1, n - 1)) + "…";
|
|
86
|
-
}
|
|
87
|
-
/**
|
|
88
|
-
* Minimal SKILL.md frontmatter parser: supports `key: value`, quoted scalars,
|
|
89
|
-
* folded blocks (`>-` / `>`) and inline `a,b` lists.
|
|
90
|
-
*/
|
|
91
|
-
function parseFrontmatter(raw) {
|
|
92
|
-
const text = raw.replace(/^/, "");
|
|
93
|
-
const m = /^---\r?\n([\s\S]*?)\r?\n---\r?\n?/.exec(text);
|
|
94
|
-
if (!m) return {
|
|
95
|
-
meta: {},
|
|
96
|
-
body: text
|
|
97
|
-
};
|
|
98
|
-
const meta = {};
|
|
99
|
-
const lines = m[1].split(/\r?\n/);
|
|
100
|
-
let key = null;
|
|
101
|
-
let folded = null;
|
|
102
|
-
const flush = () => {
|
|
103
|
-
if (key && folded) meta[key] = folded.join(" ").replace(/\s+/g, " ").trim();
|
|
104
|
-
key = null;
|
|
105
|
-
folded = null;
|
|
106
|
-
};
|
|
107
|
-
for (const line of lines) {
|
|
108
|
-
const kv = /^([A-Za-z_][\w-]*)\s*:\s*(.*)$/.exec(line);
|
|
109
|
-
if (kv && !/^\s/.test(line)) {
|
|
110
|
-
flush();
|
|
111
|
-
key = kv[1];
|
|
112
|
-
const v = kv[2].trim();
|
|
113
|
-
if (v === ">-" || v === ">" || v === "|" || v === "|-") folded = [];
|
|
114
|
-
else {
|
|
115
|
-
meta[key] = v.replace(/^["']|["']$/g, "");
|
|
116
|
-
key = null;
|
|
117
|
-
}
|
|
118
|
-
continue;
|
|
119
|
-
}
|
|
120
|
-
if (key && folded) folded.push(line.trim());
|
|
121
|
-
}
|
|
122
|
-
flush();
|
|
123
|
-
return {
|
|
124
|
-
meta,
|
|
125
|
-
body: text.slice(m[0].length)
|
|
126
|
-
};
|
|
127
|
-
}
|
|
128
|
-
function splitTags(v) {
|
|
129
|
-
return (v || "").split(/[,,;;\s]+/).map((s) => s.trim()).filter(Boolean);
|
|
130
|
-
}
|
|
131
|
-
var CJK, CJK_RUN_RE, CJK_ONLY_RE;
|
|
132
|
-
var init_text = require_rolldown_runtime.__esmMin((() => {
|
|
133
|
-
CJK = "\\u4e00-\\u9fff\\u3400-\\u4dbf\\uf900-\\ufaff";
|
|
134
|
-
new RegExp(`[${CJK}]`, "u");
|
|
135
|
-
CJK_RUN_RE = new RegExp(`[${CJK}]+|[^\\s${CJK}]+`, "gu");
|
|
136
|
-
CJK_ONLY_RE = new RegExp(`^[${CJK}]+$`, "u");
|
|
137
|
-
}));
|
|
138
|
-
//#endregion
|
|
139
23
|
//#region packages/core/database/src/db.ts
|
|
140
24
|
/**
|
|
141
25
|
* Database: single source of truth for ygl-trees.
|
|
@@ -158,7 +42,7 @@ function dbPath(home) {
|
|
|
158
42
|
}
|
|
159
43
|
var SCHEMA_SQL, DB, EDGE_RELS, EDGE_MODES, COND_KINDS;
|
|
160
44
|
var init_db = require_rolldown_runtime.__esmMin((() => {
|
|
161
|
-
init_text();
|
|
45
|
+
require_text.init_text();
|
|
162
46
|
SCHEMA_SQL = `
|
|
163
47
|
-- ---------------------------------------------------------------- meta
|
|
164
48
|
-- runtime state the tool writes itself (current selections, bookkeeping);
|
|
@@ -688,7 +572,7 @@ CREATE UNIQUE INDEX IF NOT EXISTS uq_skill_refs ON skill_refs(skill_id, path);
|
|
|
688
572
|
const group = (s.scope ? `${r[s.scope]}|` : "") + content;
|
|
689
573
|
const n = (seen.get(group) || 0) + 1;
|
|
690
574
|
seen.set(group, n);
|
|
691
|
-
const h = n > 1 ? `${sha1(content)}#dup${n}` : sha1(content);
|
|
575
|
+
const h = n > 1 ? `${require_text.sha1(content)}#dup${n}` : require_text.sha1(content);
|
|
692
576
|
this.run(`UPDATE ${s.t} SET content_hash=? WHERE rowid=?`, [h, r.__rid]);
|
|
693
577
|
}
|
|
694
578
|
}
|
|
@@ -1477,6 +1361,45 @@ var init_orm = require_rolldown_runtime.__esmMin((() => {
|
|
|
1477
1361
|
cached = null;
|
|
1478
1362
|
}));
|
|
1479
1363
|
//#endregion
|
|
1364
|
+
//#region packages/core/text/src/eventbus.ts
|
|
1365
|
+
/**
|
|
1366
|
+
* Cross-domain event bus — connects logEvent writes to real-time consumers.
|
|
1367
|
+
*
|
|
1368
|
+
* Architecture: a process-wide EventEmitter singleton. Write services call
|
|
1369
|
+
* `emitEvent()` after logEvent persists to the events table; consumers
|
|
1370
|
+
* (webui SSE, user plugins, future watchers) subscribe with `onEvent()`.
|
|
1371
|
+
*
|
|
1372
|
+
* This makes "ctx.on reactivity" real without requiring a full Cordis
|
|
1373
|
+
* event system — a lightweight bridge that the webui and plugins can use.
|
|
1374
|
+
*
|
|
1375
|
+
* @module @ygl/core-text/eventbus
|
|
1376
|
+
*/
|
|
1377
|
+
var eventbus_exports = /* @__PURE__ */ require_rolldown_runtime.__exportAll({
|
|
1378
|
+
emitEvent: () => emitEvent,
|
|
1379
|
+
onEvent: () => onEvent,
|
|
1380
|
+
onEventKind: () => onEventKind
|
|
1381
|
+
});
|
|
1382
|
+
/** Publish a cross-domain event (called after events table write). */
|
|
1383
|
+
function emitEvent(evt) {
|
|
1384
|
+
bus.emit("ygl", evt);
|
|
1385
|
+
bus.emit(`ygl:${evt.kind}`, evt);
|
|
1386
|
+
}
|
|
1387
|
+
/** Subscribe to all events. Returns an unsubscribe function. */
|
|
1388
|
+
function onEvent(handler) {
|
|
1389
|
+
bus.on("ygl", handler);
|
|
1390
|
+
return () => bus.off("ygl", handler);
|
|
1391
|
+
}
|
|
1392
|
+
/** Subscribe to a specific kind (e.g. "node.unlock"). Returns unsubscribe. */
|
|
1393
|
+
function onEventKind(kind, handler) {
|
|
1394
|
+
bus.on(`ygl:${kind}`, handler);
|
|
1395
|
+
return () => bus.off(`ygl:${kind}`, handler);
|
|
1396
|
+
}
|
|
1397
|
+
var bus;
|
|
1398
|
+
var init_eventbus = require_rolldown_runtime.__esmMin((() => {
|
|
1399
|
+
bus = new node_events.EventEmitter();
|
|
1400
|
+
bus.setMaxListeners(50);
|
|
1401
|
+
}));
|
|
1402
|
+
//#endregion
|
|
1480
1403
|
//#region packages/core/database/src/plugin.ts
|
|
1481
1404
|
/**
|
|
1482
1405
|
* DatabasePlugin — provides ctx.database (DatabaseService).
|
|
@@ -1509,6 +1432,36 @@ var DatabaseService = class extends _deepseek_ai_cordis.Service {
|
|
|
1509
1432
|
};
|
|
1510
1433
|
function apply$3(ctx, config) {
|
|
1511
1434
|
new DatabaseService(ctx, config.file);
|
|
1435
|
+
try {
|
|
1436
|
+
const { onEvent, onEventKind } = (init_eventbus(), require_rolldown_runtime.__toCommonJS(eventbus_exports));
|
|
1437
|
+
const kindSubs = [onEvent((evt) => {
|
|
1438
|
+
try {
|
|
1439
|
+
ctx.emit("ygl", evt);
|
|
1440
|
+
} catch {}
|
|
1441
|
+
})];
|
|
1442
|
+
for (const kind of [
|
|
1443
|
+
"node.unlock",
|
|
1444
|
+
"node.lock",
|
|
1445
|
+
"node.add",
|
|
1446
|
+
"node.link",
|
|
1447
|
+
"kb.add",
|
|
1448
|
+
"kb.rm",
|
|
1449
|
+
"claim.resolve",
|
|
1450
|
+
"claim.add",
|
|
1451
|
+
"task.status",
|
|
1452
|
+
"project.new",
|
|
1453
|
+
"skill.add"
|
|
1454
|
+
]) kindSubs.push(onEventKind(kind, (evt) => {
|
|
1455
|
+
try {
|
|
1456
|
+
ctx.emit(`ygl:${kind}`, evt);
|
|
1457
|
+
} catch {}
|
|
1458
|
+
}));
|
|
1459
|
+
ctx.fiber?.collect?.(() => {
|
|
1460
|
+
for (const u of kindSubs) try {
|
|
1461
|
+
u();
|
|
1462
|
+
} catch {}
|
|
1463
|
+
});
|
|
1464
|
+
} catch {}
|
|
1512
1465
|
}
|
|
1513
1466
|
//#endregion
|
|
1514
1467
|
//#region packages/web/app/src/index.ts
|
|
@@ -1942,7 +1895,7 @@ var init_eval = require_rolldown_runtime.__esmMin((() => {
|
|
|
1942
1895
|
//#endregion
|
|
1943
1896
|
//#region packages/techtree/model/src/reads.ts
|
|
1944
1897
|
init_db();
|
|
1945
|
-
init_text();
|
|
1898
|
+
require_text.init_text();
|
|
1946
1899
|
init_eval();
|
|
1947
1900
|
var TreeStore = class {
|
|
1948
1901
|
db;
|
|
@@ -2020,7 +1973,7 @@ var TreeStore = class {
|
|
|
2020
1973
|
if (p.id === c.id) throw new Error("self-loop rejected");
|
|
2021
1974
|
if (this.reaches(treeId, c.id, p.id)) throw new Error(`cycle rejected: ${childKey} already reaches ${parentKey}`);
|
|
2022
1975
|
}
|
|
2023
|
-
const id = shortId([
|
|
1976
|
+
const id = require_text.shortId([
|
|
2024
1977
|
"edge",
|
|
2025
1978
|
p.id,
|
|
2026
1979
|
c.id,
|
|
@@ -2102,7 +2055,7 @@ var TreeStore = class {
|
|
|
2102
2055
|
this.db.run("DELETE FROM node_conditions WHERE id=?", [condId]);
|
|
2103
2056
|
}
|
|
2104
2057
|
markDirty(treeId) {
|
|
2105
|
-
this.db.run("INSERT INTO node_index(tree_id,built_at,dirty) VALUES(?,?,1) ON CONFLICT(tree_id) DO UPDATE SET dirty=1", [treeId, nowIso()]);
|
|
2058
|
+
this.db.run("INSERT INTO node_index(tree_id,built_at,dirty) VALUES(?,?,1) ON CONFLICT(tree_id) DO UPDATE SET dirty=1", [treeId, require_text.nowIso()]);
|
|
2106
2059
|
}
|
|
2107
2060
|
/** Rebuild the transitive closure (BFS from every node). */
|
|
2108
2061
|
rebuildClosure(treeId) {
|
|
@@ -2219,7 +2172,7 @@ var TreeStore = class {
|
|
|
2219
2172
|
JSON.stringify(topo),
|
|
2220
2173
|
JSON.stringify(tiers),
|
|
2221
2174
|
JSON.stringify(inDegree),
|
|
2222
|
-
nowIso()
|
|
2175
|
+
require_text.nowIso()
|
|
2223
2176
|
]);
|
|
2224
2177
|
return {
|
|
2225
2178
|
topo,
|
|
@@ -2446,7 +2399,7 @@ var TreeStore = class {
|
|
|
2446
2399
|
/** Full-text search over nodes. Title/key substring hits outrank same-hit
|
|
2447
2400
|
* rows (same ranking semantics as kb/skill/source search). */
|
|
2448
2401
|
nodeSearch(treeId, q, limit = 20) {
|
|
2449
|
-
const tokens = Array.from(new Set(String((init_text(), require_rolldown_runtime.__toCommonJS(text_exports)).ngram(q) || "").split(/\s+/).filter(Boolean)));
|
|
2402
|
+
const tokens = Array.from(new Set(String((require_text.init_text(), require_rolldown_runtime.__toCommonJS(require_text.text_exports)).ngram(q) || "").split(/\s+/).filter(Boolean)));
|
|
2450
2403
|
if (!tokens.length) return [];
|
|
2451
2404
|
const agg = /* @__PURE__ */ new Map();
|
|
2452
2405
|
const st = this.db.db.prepare(`SELECT n.id,n.key,n.name,n.tier, bm25(nodes_fts) AS score
|
|
@@ -2668,7 +2621,7 @@ function apply$1(ctx) {
|
|
|
2668
2621
|
}
|
|
2669
2622
|
//#endregion
|
|
2670
2623
|
//#region packages/research/pipeline/src/reads.ts
|
|
2671
|
-
init_text();
|
|
2624
|
+
require_text.init_text();
|
|
2672
2625
|
var Store = class {
|
|
2673
2626
|
db;
|
|
2674
2627
|
constructor(db) {
|
|
@@ -2676,8 +2629,8 @@ var Store = class {
|
|
|
2676
2629
|
}
|
|
2677
2630
|
log(kind, entity = "", entityId = "", payload = "", actor = "cli") {
|
|
2678
2631
|
this.db.run("INSERT INTO events(id,ts,actor,kind,entity,entity_id,payload) VALUES(?,?,?,?,?,?,?)", [
|
|
2679
|
-
shortId([kind, entity], 12),
|
|
2680
|
-
nowIso(),
|
|
2632
|
+
require_text.shortId([kind, entity], 12),
|
|
2633
|
+
require_text.nowIso(),
|
|
2681
2634
|
actor,
|
|
2682
2635
|
kind,
|
|
2683
2636
|
entity,
|
|
@@ -2799,7 +2752,7 @@ var Store = class {
|
|
|
2799
2752
|
skillEnabled(name, on) {
|
|
2800
2753
|
return this.db.run("UPDATE skills SET enabled=?, updated=? WHERE name=?", [
|
|
2801
2754
|
on ? 1 : 0,
|
|
2802
|
-
nowIso(),
|
|
2755
|
+
require_text.nowIso(),
|
|
2803
2756
|
name
|
|
2804
2757
|
]).changes > 0;
|
|
2805
2758
|
}
|
|
@@ -2875,7 +2828,7 @@ var Store = class {
|
|
|
2875
2828
|
* works for CJK and latin alike.
|
|
2876
2829
|
*/
|
|
2877
2830
|
fts(o) {
|
|
2878
|
-
const tokens = Array.from(new Set(ngram(o.q).split(/\s+/).filter(Boolean)));
|
|
2831
|
+
const tokens = Array.from(new Set(require_text.ngram(o.q).split(/\s+/).filter(Boolean)));
|
|
2879
2832
|
if (!tokens.length) return o.fallback();
|
|
2880
2833
|
const cond = [o.where, `${o.table} MATCH ?`].filter(Boolean).join(" AND ");
|
|
2881
2834
|
const agg = /* @__PURE__ */ new Map();
|
|
@@ -2948,7 +2901,7 @@ var Store = class {
|
|
|
2948
2901
|
relate(srcType, srcId, dstType, dstId, rel = "related", weight = 1) {
|
|
2949
2902
|
this.db.run(`INSERT INTO relations(id,src_type,src_id,dst_type,dst_id,rel,weight) VALUES(?,?,?,?,?,?,?)
|
|
2950
2903
|
ON CONFLICT(src_type,src_id,dst_type,dst_id,rel) DO UPDATE SET weight=excluded.weight`, [
|
|
2951
|
-
shortId([
|
|
2904
|
+
require_text.shortId([
|
|
2952
2905
|
srcType,
|
|
2953
2906
|
srcId,
|
|
2954
2907
|
dstType,
|
|
@@ -2999,25 +2952,25 @@ var Store = class {
|
|
|
2999
2952
|
const p = (n) => String(n).padStart(2, "0");
|
|
3000
2953
|
const cut = `${cutoff.getFullYear()}-${p(cutoff.getMonth() + 1)}-${p(cutoff.getDate())} ${p(cutoff.getHours())}:${p(cutoff.getMinutes())}:${p(cutoff.getSeconds())}`;
|
|
3001
2954
|
return this.db.run(`UPDATE runs SET finished=?, rc=126, output=COALESCE(NULLIF(output,''),'') || '(reaped: process was killed mid-run)'
|
|
3002
|
-
WHERE finished='' AND started < ?`, [nowIso(), cut]).changes;
|
|
2955
|
+
WHERE finished='' AND started < ?`, [require_text.nowIso(), cut]).changes;
|
|
3003
2956
|
}
|
|
3004
2957
|
jobStart(jobId) {
|
|
3005
|
-
const id = shortId(["run", jobId], 12);
|
|
2958
|
+
const id = require_text.shortId(["run", jobId], 12);
|
|
3006
2959
|
this.db.run("INSERT INTO runs(id,job_id,started) VALUES(?,?,?)", [
|
|
3007
2960
|
id,
|
|
3008
2961
|
jobId,
|
|
3009
|
-
nowIso()
|
|
2962
|
+
require_text.nowIso()
|
|
3010
2963
|
]);
|
|
3011
2964
|
return id;
|
|
3012
2965
|
}
|
|
3013
2966
|
jobFinish(runId, rc, output) {
|
|
3014
2967
|
this.db.run("UPDATE runs SET finished=?, rc=?, output=? WHERE id=?", [
|
|
3015
|
-
nowIso(),
|
|
2968
|
+
require_text.nowIso(),
|
|
3016
2969
|
rc,
|
|
3017
2970
|
output.slice(0, 8e3)
|
|
3018
2971
|
]);
|
|
3019
2972
|
this.db.run("UPDATE jobs SET runs=runs+1, last_run=?, status=? WHERE id=(SELECT job_id FROM runs WHERE id=?)", [
|
|
3020
|
-
nowIso(),
|
|
2973
|
+
require_text.nowIso(),
|
|
3021
2974
|
rc === 0 ? "ok" : "failed",
|
|
3022
2975
|
runId
|
|
3023
2976
|
]);
|
|
@@ -3060,7 +3013,8 @@ function str(v) {
|
|
|
3060
3013
|
*/
|
|
3061
3014
|
function deriveL1(body, title) {
|
|
3062
3015
|
const lines = body.split("\n").map((l) => l.replace(/\*\*/g, "").trim()).filter(Boolean).filter((l) => !/^#{1,6}\s/.test(l)).filter((l) => !/^_generated/i.test(l) && !/^generated/i.test(l));
|
|
3063
|
-
|
|
3016
|
+
const pick = (lines.slice(0, 20).find((l) => /^[-*]\s+|^\d+[.)]\s+/.test(l)) || lines[0] || title).replace(/^[-*]\s+|^\d+[.)]\s+/, "").replace(/^[✓✗⚠?*☐☑]\s*/, "").replace(/\s*\[\d+\]/g, "").replace(/\s+/g, " ").trim();
|
|
3017
|
+
return `${require_text.clip(pick, 200)}(提炼自《${require_text.clip(title, 60)}》)`;
|
|
3064
3018
|
}
|
|
3065
3019
|
//#endregion
|
|
3066
3020
|
//#region packages/research/pipeline/src/plugin.ts
|
|
@@ -3180,18 +3134,21 @@ function writeUserBundle(home, specs) {
|
|
|
3180
3134
|
function pnpm(home, args) {
|
|
3181
3135
|
const pm = process.env.YGL_PACKAGE_MANAGER || "pnpm";
|
|
3182
3136
|
if (process.platform === "win32") {
|
|
3183
|
-
const q = (s) => `"${String(s).replace(/["&|<>^]/g, "")}"`;
|
|
3184
3137
|
const exe = resolvePm(pm);
|
|
3185
|
-
(
|
|
3186
|
-
|
|
3187
|
-
|
|
3138
|
+
const { spawnSync } = require("node:child_process");
|
|
3139
|
+
const r = spawnSync("cmd", [
|
|
3140
|
+
"/c",
|
|
3141
|
+
exe,
|
|
3142
|
+
...args,
|
|
3188
3143
|
"--dir",
|
|
3189
|
-
|
|
3144
|
+
profileDir(home),
|
|
3190
3145
|
"--ignore-workspace"
|
|
3191
|
-
]
|
|
3192
|
-
|
|
3193
|
-
|
|
3194
|
-
|
|
3146
|
+
], { stdio: "pipe" });
|
|
3147
|
+
if (r.status !== 0) {
|
|
3148
|
+
const err = new Error(String(r.stderr || r.stdout || `pnpm exited ${r.status}`));
|
|
3149
|
+
err.status = r.status;
|
|
3150
|
+
throw err;
|
|
3151
|
+
}
|
|
3195
3152
|
return;
|
|
3196
3153
|
}
|
|
3197
3154
|
(0, node_child_process.execFileSync)(pm, [
|
|
@@ -3225,6 +3182,16 @@ function resolvePm(pm) {
|
|
|
3225
3182
|
async function installPlugin(home, spec) {
|
|
3226
3183
|
initProfile(home);
|
|
3227
3184
|
const abs = node_path.resolve(spec);
|
|
3185
|
+
if (node_fs.existsSync(abs) && node_fs.statSync(abs).isDirectory()) {
|
|
3186
|
+
const pkgPath = node_path.join(abs, "package.json");
|
|
3187
|
+
if (!node_fs.existsSync(pkgPath)) throw new Error(`local plugin directory has no package.json: ${abs}`);
|
|
3188
|
+
try {
|
|
3189
|
+
const pkg = JSON.parse(node_fs.readFileSync(pkgPath, "utf8"));
|
|
3190
|
+
if (!pkg.name || typeof pkg.name !== "string") throw new Error(`package.json missing "name" field: ${abs}`);
|
|
3191
|
+
} catch (e) {
|
|
3192
|
+
throw new Error(`invalid package.json in ${abs}: ${e?.message || e}`);
|
|
3193
|
+
}
|
|
3194
|
+
} else if (spec.startsWith(".") || spec.startsWith("/") || spec.startsWith("\\") || /^[A-Z]:/.test(spec)) throw new Error(`plugin path not found: ${abs}`);
|
|
3228
3195
|
const installSpec = node_fs.existsSync(abs) && node_fs.statSync(abs).isDirectory() ? `link:${abs}` : spec;
|
|
3229
3196
|
const existing = readUserBundle(home).find((p) => p.spec === installSpec || p.spec === spec);
|
|
3230
3197
|
if (existing) return existing;
|
|
@@ -3509,6 +3476,7 @@ function createProcessShutdown(dispose, forceExit = (code) => process.exit(code)
|
|
|
3509
3476
|
}
|
|
3510
3477
|
//#endregion
|
|
3511
3478
|
//#region apps/cli/src/plugin.ts
|
|
3479
|
+
var plugin_exports = /* @__PURE__ */ require_rolldown_runtime.__exportAll({ runPluginCommand: () => runPluginCommand });
|
|
3512
3480
|
init_plugins();
|
|
3513
3481
|
function runPluginCommand(env, action, rest, args) {
|
|
3514
3482
|
const { ctx } = env;
|
|
@@ -3632,7 +3600,7 @@ function runPluginCommand(env, action, rest, args) {
|
|
|
3632
3600
|
}
|
|
3633
3601
|
//#endregion
|
|
3634
3602
|
//#region packages/ops/tools/src/pgsync.ts
|
|
3635
|
-
init_text();
|
|
3603
|
+
require_text.init_text();
|
|
3636
3604
|
/** Mirror targets, FK-dependency-safe order (same list as `db export`). */
|
|
3637
3605
|
const MIRROR_TABLES = [
|
|
3638
3606
|
"meta",
|
|
@@ -3691,7 +3659,7 @@ async function copyTable(client, db, t) {
|
|
|
3691
3659
|
const v = r[c];
|
|
3692
3660
|
return v === void 0 ? null : v;
|
|
3693
3661
|
});
|
|
3694
|
-
if (NGRAM_INPUT[t]) vals.push(ngram(NGRAM_INPUT[t](r)));
|
|
3662
|
+
if (NGRAM_INPUT[t]) vals.push(require_text.ngram(NGRAM_INPUT[t](r)));
|
|
3695
3663
|
params.push(...vals);
|
|
3696
3664
|
return `(${vals.map((_, j) => `$${params.length - vals.length + j + 1}`).join(",")})`;
|
|
3697
3665
|
});
|
|
@@ -3989,45 +3957,6 @@ function preflightTypeCheck(db) {
|
|
|
3989
3957
|
return issues;
|
|
3990
3958
|
}
|
|
3991
3959
|
//#endregion
|
|
3992
|
-
//#region packages/core/text/src/eventbus.ts
|
|
3993
|
-
/**
|
|
3994
|
-
* Cross-domain event bus — connects logEvent writes to real-time consumers.
|
|
3995
|
-
*
|
|
3996
|
-
* Architecture: a process-wide EventEmitter singleton. Write services call
|
|
3997
|
-
* `emitEvent()` after logEvent persists to the events table; consumers
|
|
3998
|
-
* (webui SSE, user plugins, future watchers) subscribe with `onEvent()`.
|
|
3999
|
-
*
|
|
4000
|
-
* This makes "ctx.on reactivity" real without requiring a full Cordis
|
|
4001
|
-
* event system — a lightweight bridge that the webui and plugins can use.
|
|
4002
|
-
*
|
|
4003
|
-
* @module @ygl/core-text/eventbus
|
|
4004
|
-
*/
|
|
4005
|
-
var eventbus_exports = /* @__PURE__ */ require_rolldown_runtime.__exportAll({
|
|
4006
|
-
emitEvent: () => emitEvent,
|
|
4007
|
-
onEvent: () => onEvent,
|
|
4008
|
-
onEventKind: () => onEventKind
|
|
4009
|
-
});
|
|
4010
|
-
/** Publish a cross-domain event (called after events table write). */
|
|
4011
|
-
function emitEvent(evt) {
|
|
4012
|
-
bus.emit("ygl", evt);
|
|
4013
|
-
bus.emit(`ygl:${evt.kind}`, evt);
|
|
4014
|
-
}
|
|
4015
|
-
/** Subscribe to all events. Returns an unsubscribe function. */
|
|
4016
|
-
function onEvent(handler) {
|
|
4017
|
-
bus.on("ygl", handler);
|
|
4018
|
-
return () => bus.off("ygl", handler);
|
|
4019
|
-
}
|
|
4020
|
-
/** Subscribe to a specific kind (e.g. "node.unlock"). Returns unsubscribe. */
|
|
4021
|
-
function onEventKind(kind, handler) {
|
|
4022
|
-
bus.on(`ygl:${kind}`, handler);
|
|
4023
|
-
return () => bus.off(`ygl:${kind}`, handler);
|
|
4024
|
-
}
|
|
4025
|
-
var bus;
|
|
4026
|
-
var init_eventbus = require_rolldown_runtime.__esmMin((() => {
|
|
4027
|
-
bus = new node_events.EventEmitter();
|
|
4028
|
-
bus.setMaxListeners(50);
|
|
4029
|
-
}));
|
|
4030
|
-
//#endregion
|
|
4031
3960
|
//#region packages/research/pipeline/src/writes.ts
|
|
4032
3961
|
var writes_exports = /* @__PURE__ */ require_rolldown_runtime.__exportAll({
|
|
4033
3962
|
artifactAdd: () => artifactAdd,
|
|
@@ -4059,8 +3988,8 @@ async function logEvent$1(mgr, kind, entity, entityId, payload, level = "info")
|
|
|
4059
3988
|
};
|
|
4060
3989
|
const p = typeof obj === "string" ? obj : JSON.stringify(obj);
|
|
4061
3990
|
await mgr.insert(Event, {
|
|
4062
|
-
id: shortId([kind, entity], 12),
|
|
4063
|
-
ts: nowIso(),
|
|
3991
|
+
id: require_text.shortId([kind, entity], 12),
|
|
3992
|
+
ts: require_text.nowIso(),
|
|
4064
3993
|
actor: "cli",
|
|
4065
3994
|
kind,
|
|
4066
3995
|
entity,
|
|
@@ -4080,7 +4009,7 @@ async function logEvent$1(mgr, kind, entity, entityId, payload, level = "info")
|
|
|
4080
4009
|
} catch {}
|
|
4081
4010
|
}
|
|
4082
4011
|
async function queryAdd(ds, projectId, text, engine = "", force = false) {
|
|
4083
|
-
const hash = contentHash(text, force);
|
|
4012
|
+
const hash = require_text.contentHash(text, force);
|
|
4084
4013
|
return ds.transaction(async (mgr) => {
|
|
4085
4014
|
const ex = await mgr.findOne(Query, { where: {
|
|
4086
4015
|
projectId,
|
|
@@ -4091,7 +4020,7 @@ async function queryAdd(ds, projectId, text, engine = "", force = false) {
|
|
|
4091
4020
|
dup: true
|
|
4092
4021
|
};
|
|
4093
4022
|
const q = new Query();
|
|
4094
|
-
q.id = shortId([
|
|
4023
|
+
q.id = require_text.shortId([
|
|
4095
4024
|
"q",
|
|
4096
4025
|
projectId,
|
|
4097
4026
|
text
|
|
@@ -4102,7 +4031,7 @@ async function queryAdd(ds, projectId, text, engine = "", force = false) {
|
|
|
4102
4031
|
q.status = "pending";
|
|
4103
4032
|
q.note = "";
|
|
4104
4033
|
q.contentHash = hash;
|
|
4105
|
-
q.created = nowIso();
|
|
4034
|
+
q.created = require_text.nowIso();
|
|
4106
4035
|
await mgr.save(q);
|
|
4107
4036
|
await logEvent$1(mgr, "query.add", "query", q.id, text);
|
|
4108
4037
|
return {
|
|
@@ -4125,7 +4054,7 @@ function mapQuery(q) {
|
|
|
4125
4054
|
}
|
|
4126
4055
|
async function sourceAdd(ds, projectId, o) {
|
|
4127
4056
|
const url = o.url || "";
|
|
4128
|
-
const urlHash = sha1(url || o.title || "");
|
|
4057
|
+
const urlHash = require_text.sha1(url || o.title || "");
|
|
4129
4058
|
return ds.transaction(async (mgr) => {
|
|
4130
4059
|
const ex = await mgr.findOne(Source, { where: {
|
|
4131
4060
|
projectId,
|
|
@@ -4140,7 +4069,7 @@ async function sourceAdd(ds, projectId, o) {
|
|
|
4140
4069
|
const abstract_ = o.abstract || "";
|
|
4141
4070
|
const content = o.content || "";
|
|
4142
4071
|
const s = new Source();
|
|
4143
|
-
s.id = shortId([
|
|
4072
|
+
s.id = require_text.shortId([
|
|
4144
4073
|
"src",
|
|
4145
4074
|
projectId,
|
|
4146
4075
|
urlHash
|
|
@@ -4149,22 +4078,22 @@ async function sourceAdd(ds, projectId, o) {
|
|
|
4149
4078
|
s.url = url;
|
|
4150
4079
|
s.title = title;
|
|
4151
4080
|
s.urlHash = urlHash;
|
|
4152
|
-
s.contentHash = sha1(content || abstract_);
|
|
4081
|
+
s.contentHash = require_text.sha1(content || abstract_);
|
|
4153
4082
|
s.abstract = abstract_;
|
|
4154
4083
|
s.content = content;
|
|
4155
4084
|
s.engine = o.engine || "";
|
|
4156
4085
|
s.relevance = o.relevance ?? 0;
|
|
4157
4086
|
s.confidence = o.confidence || "B";
|
|
4158
4087
|
s.tags = o.tags || "";
|
|
4159
|
-
s.retrievedAt = nowIso();
|
|
4160
|
-
s.created = nowIso();
|
|
4088
|
+
s.retrievedAt = require_text.nowIso();
|
|
4089
|
+
s.created = require_text.nowIso();
|
|
4161
4090
|
await mgr.save(s);
|
|
4162
4091
|
await mgr.query(`INSERT INTO sources_fts(id,title,abstract,content,ngram) VALUES(?,?,?,?,?)`, [
|
|
4163
4092
|
s.id,
|
|
4164
4093
|
title,
|
|
4165
4094
|
abstract_,
|
|
4166
4095
|
content,
|
|
4167
|
-
ngram(`${title} ${abstract_} ${content} ${o.tags || ""}`)
|
|
4096
|
+
require_text.ngram(`${title} ${abstract_} ${content} ${o.tags || ""}`)
|
|
4168
4097
|
]);
|
|
4169
4098
|
await logEvent$1(mgr, "source.add", "source", s.id, title);
|
|
4170
4099
|
return {
|
|
@@ -4192,7 +4121,7 @@ function mapSource(s) {
|
|
|
4192
4121
|
};
|
|
4193
4122
|
}
|
|
4194
4123
|
async function evidenceAdd(ds, projectId, sourceId, quote, note = "", locator = "", force = false) {
|
|
4195
|
-
const hash = contentHash(quote, force);
|
|
4124
|
+
const hash = require_text.contentHash(quote, force);
|
|
4196
4125
|
return ds.transaction(async (mgr) => {
|
|
4197
4126
|
if (!await mgr.findOne(Source, { where: {
|
|
4198
4127
|
id: sourceId,
|
|
@@ -4207,7 +4136,7 @@ async function evidenceAdd(ds, projectId, sourceId, quote, note = "", locator =
|
|
|
4207
4136
|
dup: true
|
|
4208
4137
|
};
|
|
4209
4138
|
const e = new Evidence();
|
|
4210
|
-
e.id = shortId([
|
|
4139
|
+
e.id = require_text.shortId([
|
|
4211
4140
|
"ev",
|
|
4212
4141
|
sourceId,
|
|
4213
4142
|
quote
|
|
@@ -4218,12 +4147,12 @@ async function evidenceAdd(ds, projectId, sourceId, quote, note = "", locator =
|
|
|
4218
4147
|
e.note = note;
|
|
4219
4148
|
e.locator = locator;
|
|
4220
4149
|
e.contentHash = hash;
|
|
4221
|
-
e.created = nowIso();
|
|
4150
|
+
e.created = require_text.nowIso();
|
|
4222
4151
|
await mgr.save(e);
|
|
4223
4152
|
await mgr.query(`INSERT INTO evidence_fts(id,quote,ngram) VALUES(?,?,?)`, [
|
|
4224
4153
|
e.id,
|
|
4225
4154
|
quote,
|
|
4226
|
-
ngram(quote)
|
|
4155
|
+
require_text.ngram(quote)
|
|
4227
4156
|
]);
|
|
4228
4157
|
await logEvent$1(mgr, "evidence.add", "evidence", e.id, quote.slice(0, 60));
|
|
4229
4158
|
return {
|
|
@@ -4245,7 +4174,7 @@ function mapEvidence(e) {
|
|
|
4245
4174
|
};
|
|
4246
4175
|
}
|
|
4247
4176
|
async function claimAdd(ds, projectId, text, confidence = "B", force = false) {
|
|
4248
|
-
const hash = contentHash(text, force);
|
|
4177
|
+
const hash = require_text.contentHash(text, force);
|
|
4249
4178
|
return ds.transaction(async (mgr) => {
|
|
4250
4179
|
const ex = await mgr.findOne(Claim, { where: {
|
|
4251
4180
|
projectId,
|
|
@@ -4256,7 +4185,7 @@ async function claimAdd(ds, projectId, text, confidence = "B", force = false) {
|
|
|
4256
4185
|
dup: true
|
|
4257
4186
|
};
|
|
4258
4187
|
const c = new Claim();
|
|
4259
|
-
c.id = shortId([
|
|
4188
|
+
c.id = require_text.shortId([
|
|
4260
4189
|
"cl",
|
|
4261
4190
|
projectId,
|
|
4262
4191
|
text
|
|
@@ -4266,8 +4195,8 @@ async function claimAdd(ds, projectId, text, confidence = "B", force = false) {
|
|
|
4266
4195
|
c.status = "unverified";
|
|
4267
4196
|
c.confidence = confidence;
|
|
4268
4197
|
c.contentHash = hash;
|
|
4269
|
-
c.created = nowIso();
|
|
4270
|
-
c.updated = nowIso();
|
|
4198
|
+
c.created = require_text.nowIso();
|
|
4199
|
+
c.updated = require_text.nowIso();
|
|
4271
4200
|
await mgr.save(c);
|
|
4272
4201
|
await logEvent$1(mgr, "claim.add", "claim", c.id, text.slice(0, 60));
|
|
4273
4202
|
return {
|
|
@@ -4311,7 +4240,7 @@ async function claimResolve(ds, claimId, status, note = "") {
|
|
|
4311
4240
|
return ds.transaction(async (mgr) => {
|
|
4312
4241
|
await mgr.update(Claim, { id: claimId }, {
|
|
4313
4242
|
status,
|
|
4314
|
-
updated: nowIso()
|
|
4243
|
+
updated: require_text.nowIso()
|
|
4315
4244
|
});
|
|
4316
4245
|
await logEvent$1(mgr, "claim.resolve", "claim", claimId, `${status}${note ? " | " + note : ""}`);
|
|
4317
4246
|
});
|
|
@@ -4340,7 +4269,7 @@ async function queryAttach(ds, projectId, queryIdOrText, sourceId, note = "") {
|
|
|
4340
4269
|
qs.queryId = q.id;
|
|
4341
4270
|
qs.sourceId = s.id;
|
|
4342
4271
|
qs.note = note;
|
|
4343
|
-
qs.created = nowIso();
|
|
4272
|
+
qs.created = require_text.nowIso();
|
|
4344
4273
|
await mgr.save(qs);
|
|
4345
4274
|
await logEvent$1(mgr, "query.attach", "query", q.id, s.id);
|
|
4346
4275
|
}
|
|
@@ -4353,15 +4282,15 @@ async function queryAttach(ds, projectId, queryIdOrText, sourceId, note = "") {
|
|
|
4353
4282
|
});
|
|
4354
4283
|
}
|
|
4355
4284
|
async function kbAdd(ds, o) {
|
|
4356
|
-
const hash = contentHash(`${o.title}\n${o.body}`, !!o.force);
|
|
4285
|
+
const hash = require_text.contentHash(`${o.title}\n${o.body}`, !!o.force);
|
|
4357
4286
|
return ds.transaction(async (mgr) => {
|
|
4358
4287
|
const ex = await mgr.query(`SELECT * FROM kb_notes WHERE content_hash=?`, [hash]);
|
|
4359
4288
|
if (ex.length) return {
|
|
4360
4289
|
row: ex[0],
|
|
4361
4290
|
dup: true
|
|
4362
4291
|
};
|
|
4363
|
-
const id = shortId(["kb", o.title], 10);
|
|
4364
|
-
const now = nowIso();
|
|
4292
|
+
const id = require_text.shortId(["kb", o.title], 10);
|
|
4293
|
+
const now = require_text.nowIso();
|
|
4365
4294
|
await mgr.query(`INSERT INTO kb_notes(id,title,body,source_url,origin,tags,confidence,reuse,content_hash,created,updated)
|
|
4366
4295
|
VALUES(?,?,?,?,?,?,?,0,?,?,?)`, [
|
|
4367
4296
|
id,
|
|
@@ -4379,7 +4308,7 @@ async function kbAdd(ds, o) {
|
|
|
4379
4308
|
id,
|
|
4380
4309
|
o.title,
|
|
4381
4310
|
o.tags || "",
|
|
4382
|
-
ngram(`${o.title} ${o.tags || ""} ${o.body}`)
|
|
4311
|
+
require_text.ngram(`${o.title} ${o.tags || ""} ${o.body}`)
|
|
4383
4312
|
]);
|
|
4384
4313
|
await logEvent$1(mgr, "kb.add", "kb_note", id, o.title);
|
|
4385
4314
|
return {
|
|
@@ -4417,13 +4346,13 @@ async function kbImportBulk(ds, items) {
|
|
|
4417
4346
|
let added = 0;
|
|
4418
4347
|
let dups = 0;
|
|
4419
4348
|
for (const o of items) {
|
|
4420
|
-
const hash = contentHash(`${o.title}\n${o.body}`, false);
|
|
4349
|
+
const hash = require_text.contentHash(`${o.title}\n${o.body}`, false);
|
|
4421
4350
|
if ((await mgr.query(`SELECT id FROM kb_notes WHERE content_hash=?`, [hash])).length) {
|
|
4422
4351
|
dups++;
|
|
4423
4352
|
continue;
|
|
4424
4353
|
}
|
|
4425
|
-
const id = shortId(["kb", o.title], 10);
|
|
4426
|
-
const now = nowIso();
|
|
4354
|
+
const id = require_text.shortId(["kb", o.title], 10);
|
|
4355
|
+
const now = require_text.nowIso();
|
|
4427
4356
|
await mgr.query(`INSERT INTO kb_notes(id,title,body,source_url,origin,tags,confidence,reuse,content_hash,created,updated)
|
|
4428
4357
|
VALUES(?,?,?,?,?,?,?,0,?,?,?)`, [
|
|
4429
4358
|
id,
|
|
@@ -4441,7 +4370,7 @@ async function kbImportBulk(ds, items) {
|
|
|
4441
4370
|
id,
|
|
4442
4371
|
o.title,
|
|
4443
4372
|
o.tags || "",
|
|
4444
|
-
ngram(`${o.title} ${o.tags || ""} ${o.body}`)
|
|
4373
|
+
require_text.ngram(`${o.title} ${o.tags || ""} ${o.body}`)
|
|
4445
4374
|
]);
|
|
4446
4375
|
await logEvent$1(mgr, "kb.add", "kb_note", id, o.title);
|
|
4447
4376
|
added++;
|
|
@@ -4464,8 +4393,8 @@ async function jobAdd(ds, o) {
|
|
|
4464
4393
|
let i = 2;
|
|
4465
4394
|
while ((await mgr.query(`SELECT 1 AS hit FROM jobs WHERE title=?`, [title])).length) title = `${o.title}-${i++}`;
|
|
4466
4395
|
}
|
|
4467
|
-
const id = shortId(["job", title], 10);
|
|
4468
|
-
const created = nowIso();
|
|
4396
|
+
const id = require_text.shortId(["job", title], 10);
|
|
4397
|
+
const created = require_text.nowIso();
|
|
4469
4398
|
await mgr.query(`INSERT INTO jobs(id,title,command,every_minutes,at,enabled,runs,last_run,status,created)
|
|
4470
4399
|
VALUES(?,?,?,?,?,1,0,'','pending',?)`, [
|
|
4471
4400
|
id,
|
|
@@ -4501,14 +4430,14 @@ async function artifactAdd(ds, projectId, kind, title, content, format = "markdo
|
|
|
4501
4430
|
title
|
|
4502
4431
|
]);
|
|
4503
4432
|
const ver = Number(max?.[0]?.m ?? 0) + 1;
|
|
4504
|
-
const id = shortId([
|
|
4433
|
+
const id = require_text.shortId([
|
|
4505
4434
|
"art",
|
|
4506
4435
|
projectId,
|
|
4507
4436
|
kind,
|
|
4508
4437
|
title,
|
|
4509
4438
|
String(ver)
|
|
4510
4439
|
], 10);
|
|
4511
|
-
const created = nowIso();
|
|
4440
|
+
const created = require_text.nowIso();
|
|
4512
4441
|
await mgr.query(`INSERT INTO artifacts(id,project_id,kind,title,format,content,version,created,meta) VALUES(?,?,?,?,?,?,?,?,?)`, [
|
|
4513
4442
|
id,
|
|
4514
4443
|
projectId,
|
|
@@ -4557,7 +4486,7 @@ async function taskSetStatus(ds, taskId, status) {
|
|
|
4557
4486
|
...meta,
|
|
4558
4487
|
status
|
|
4559
4488
|
}),
|
|
4560
|
-
nowIso(),
|
|
4489
|
+
require_text.nowIso(),
|
|
4561
4490
|
taskId
|
|
4562
4491
|
]);
|
|
4563
4492
|
await logEvent$1(mgr, "task.status", "task", taskId, `${from} → ${status}`, status === "done" ? "info" : "info");
|
|
@@ -4571,13 +4500,13 @@ async function taskSetStatus(ds, taskId, status) {
|
|
|
4571
4500
|
}
|
|
4572
4501
|
async function skillUpsert(ds, o) {
|
|
4573
4502
|
return ds.transaction(async (mgr) => {
|
|
4574
|
-
const now = nowIso();
|
|
4503
|
+
const now = require_text.nowIso();
|
|
4575
4504
|
await mgr.query(`INSERT INTO skills(id,name,version,description,body,tags,origin,created,updated)
|
|
4576
4505
|
VALUES(?,?,?,?,?,?,?,?,?)
|
|
4577
4506
|
ON CONFLICT(name) DO UPDATE SET
|
|
4578
4507
|
version=excluded.version, description=excluded.description, body=excluded.body,
|
|
4579
4508
|
tags=excluded.tags, origin=excluded.origin, updated=excluded.updated`, [
|
|
4580
|
-
shortId(["skill", o.name], 10),
|
|
4509
|
+
require_text.shortId(["skill", o.name], 10),
|
|
4581
4510
|
o.name,
|
|
4582
4511
|
o.version || "0.1.0",
|
|
4583
4512
|
o.description || "",
|
|
@@ -4594,7 +4523,7 @@ async function skillUpsert(ds, o) {
|
|
|
4594
4523
|
s.name,
|
|
4595
4524
|
s.description,
|
|
4596
4525
|
s.tags,
|
|
4597
|
-
ngram(`${s.name} ${s.description} ${s.tags} ${s.body}`)
|
|
4526
|
+
require_text.ngram(`${s.name} ${s.description} ${s.tags} ${s.body}`)
|
|
4598
4527
|
]);
|
|
4599
4528
|
await logEvent$1(mgr, "skill.upsert", "skill", s.id, s.name);
|
|
4600
4529
|
return s;
|
|
@@ -4614,7 +4543,7 @@ async function skillEnabled(ds, name, on) {
|
|
|
4614
4543
|
if (!rows.length) return false;
|
|
4615
4544
|
await mgr.query(`UPDATE skills SET enabled=?, updated=? WHERE id=?`, [
|
|
4616
4545
|
on ? 1 : 0,
|
|
4617
|
-
nowIso(),
|
|
4546
|
+
require_text.nowIso(),
|
|
4618
4547
|
rows[0].id
|
|
4619
4548
|
]);
|
|
4620
4549
|
return true;
|
|
@@ -4624,7 +4553,7 @@ async function skillRefAdd(ds, skillName, refPath, content) {
|
|
|
4624
4553
|
return ds.transaction(async (mgr) => {
|
|
4625
4554
|
const s = await mgr.query(`SELECT id FROM skills WHERE name=?`, [skillName]);
|
|
4626
4555
|
if (!s.length) throw new Error(`skill not found: ${skillName}`);
|
|
4627
|
-
const id = shortId([
|
|
4556
|
+
const id = require_text.shortId([
|
|
4628
4557
|
"ref",
|
|
4629
4558
|
s[0].id,
|
|
4630
4559
|
refPath
|
|
@@ -4649,8 +4578,8 @@ async function projectCreate(ds, name, question = "") {
|
|
|
4649
4578
|
duplicate: true
|
|
4650
4579
|
};
|
|
4651
4580
|
}
|
|
4652
|
-
const now = nowIso();
|
|
4653
|
-
const id = shortId(["proj", name], 10);
|
|
4581
|
+
const now = require_text.nowIso();
|
|
4582
|
+
const id = require_text.shortId(["proj", name], 10);
|
|
4654
4583
|
await mgr.query(`INSERT INTO projects(id,name,question,status,created,updated) VALUES(?,?,?,'active',?,?)`, [
|
|
4655
4584
|
id,
|
|
4656
4585
|
name,
|
|
@@ -4667,7 +4596,7 @@ var TASK_STATUSES;
|
|
|
4667
4596
|
var init_writes = require_rolldown_runtime.__esmMin((() => {
|
|
4668
4597
|
init_entities$1();
|
|
4669
4598
|
init_entities();
|
|
4670
|
-
init_text();
|
|
4599
|
+
require_text.init_text();
|
|
4671
4600
|
TASK_STATUSES = [
|
|
4672
4601
|
"todo",
|
|
4673
4602
|
"doing",
|
|
@@ -4708,7 +4637,7 @@ async function autoImportBuiltinSkills(env, dbFile) {
|
|
|
4708
4637
|
}
|
|
4709
4638
|
const { getOrm } = (init_orm(), require_rolldown_runtime.__toCommonJS(orm_exports));
|
|
4710
4639
|
const writes = (init_writes(), require_rolldown_runtime.__toCommonJS(writes_exports));
|
|
4711
|
-
const { parseFrontmatter } = (init_text(), require_rolldown_runtime.__toCommonJS(text_exports));
|
|
4640
|
+
const { parseFrontmatter } = (require_text.init_text(), require_rolldown_runtime.__toCommonJS(require_text.text_exports));
|
|
4712
4641
|
const ds = await getOrm(dbFile);
|
|
4713
4642
|
let count = 0;
|
|
4714
4643
|
for (const entry of fs2.readdirSync(skillsDir)) {
|
|
@@ -5239,7 +5168,7 @@ function sqlLit(v) {
|
|
|
5239
5168
|
}
|
|
5240
5169
|
//#endregion
|
|
5241
5170
|
//#region packages/ops/tools/src/config.ts
|
|
5242
|
-
init_text();
|
|
5171
|
+
require_text.init_text();
|
|
5243
5172
|
const CONFIG_REGISTRY = [
|
|
5244
5173
|
{
|
|
5245
5174
|
key: "eval.pass_threshold",
|
|
@@ -5352,11 +5281,11 @@ function configSet(db, key, value) {
|
|
|
5352
5281
|
key,
|
|
5353
5282
|
v,
|
|
5354
5283
|
spec.note,
|
|
5355
|
-
nowIso()
|
|
5284
|
+
require_text.nowIso()
|
|
5356
5285
|
]);
|
|
5357
5286
|
db.run("INSERT INTO events(id,ts,actor,kind,entity,entity_id,payload) VALUES(?,?,?,?,?,?,?)", [
|
|
5358
5287
|
`${key}-${Date.now()}-${Math.random().toString(16).slice(2, 8)}`,
|
|
5359
|
-
nowIso(),
|
|
5288
|
+
require_text.nowIso(),
|
|
5360
5289
|
"cli",
|
|
5361
5290
|
"config.set",
|
|
5362
5291
|
"config",
|
|
@@ -5469,7 +5398,7 @@ function run$11(env, action, rest, args) {
|
|
|
5469
5398
|
* Writes (add) run on the TypeORM write service (src/writes.ts). */
|
|
5470
5399
|
var job_cmds_exports = /* @__PURE__ */ require_rolldown_runtime.__exportAll({ run: () => run$10 });
|
|
5471
5400
|
init_fmt();
|
|
5472
|
-
init_text();
|
|
5401
|
+
require_text.init_text();
|
|
5473
5402
|
init_orm();
|
|
5474
5403
|
init_writes();
|
|
5475
5404
|
function run$10(env, action, rest, args) {
|
|
@@ -5617,7 +5546,7 @@ function execute(env, job) {
|
|
|
5617
5546
|
store.jobFinish(runId, rc, output);
|
|
5618
5547
|
if (rc === 0) ok(ctx, `${job.title} ok ${ms}ms`);
|
|
5619
5548
|
else bad(ctx, `${job.title} rc=${rc} ${output.slice(0, 160)}`);
|
|
5620
|
-
store.log("job.run", "job", job.id, `rc=${rc} ${nowIso()}`);
|
|
5549
|
+
store.log("job.run", "job", job.id, `rc=${rc} ${require_text.nowIso()}`);
|
|
5621
5550
|
}
|
|
5622
5551
|
/**
|
|
5623
5552
|
* Concurrency guard for `job tick`: mkdir-based lock (same primitive the
|
|
@@ -5677,7 +5606,7 @@ var agent_cmds_exports = /* @__PURE__ */ require_rolldown_runtime.__exportAll({
|
|
|
5677
5606
|
run: () => run$9
|
|
5678
5607
|
});
|
|
5679
5608
|
init_fmt();
|
|
5680
|
-
init_text();
|
|
5609
|
+
require_text.init_text();
|
|
5681
5610
|
/** Build the brief payload (where am I / what exists / what next).
|
|
5682
5611
|
* Shared by the `agent brief` command and the WebUI dashboard. */
|
|
5683
5612
|
function buildBrief(env) {
|
|
@@ -5695,7 +5624,7 @@ function buildBrief(env) {
|
|
|
5695
5624
|
counts: stats,
|
|
5696
5625
|
top_skills: skills.map((s) => ({
|
|
5697
5626
|
name: s.name,
|
|
5698
|
-
description: clip(s.description, 120)
|
|
5627
|
+
description: require_text.clip(s.description, 120)
|
|
5699
5628
|
})),
|
|
5700
5629
|
recent_notes: notes.map((n) => ({
|
|
5701
5630
|
id: n.id,
|
|
@@ -5722,7 +5651,7 @@ function buildBrief(env) {
|
|
|
5722
5651
|
};
|
|
5723
5652
|
payload.unverified_claims = claims.filter((c) => c.status !== "supported").map((c) => ({
|
|
5724
5653
|
id: c.id,
|
|
5725
|
-
text: clip(c.text, 80),
|
|
5654
|
+
text: require_text.clip(c.text, 80),
|
|
5726
5655
|
status: c.status
|
|
5727
5656
|
}));
|
|
5728
5657
|
if (!src.length) payload.next_actions.push(`ygl-trees research source add --title "..." --url "..."`);
|
|
@@ -5930,7 +5859,7 @@ function run$9(env, action, rest, args) {
|
|
|
5930
5859
|
out(ctx, ` counts skills ${stats.skills} · kb ${stats.kb_notes} · jobs ${stats.jobs} · events ${stats.events}`);
|
|
5931
5860
|
if (skills.length) {
|
|
5932
5861
|
out(ctx, paint(C.bold, "\n available skills", ctx.color));
|
|
5933
|
-
for (const s of skills) out(ctx, ` - ${s.name} ${paint(C.dim, clip(s.description, 90), ctx.color)}`);
|
|
5862
|
+
for (const s of skills) out(ctx, ` - ${s.name} ${paint(C.dim, require_text.clip(s.description, 90), ctx.color)}`);
|
|
5934
5863
|
}
|
|
5935
5864
|
out(ctx, paint(C.bold, "\n next actions", ctx.color));
|
|
5936
5865
|
for (const a of payload.next_actions) out(ctx, ` → ${a}`);
|
|
@@ -6220,7 +6149,7 @@ var init_eval_enhance = require_rolldown_runtime.__esmMin((() => {
|
|
|
6220
6149
|
* List commands run on TypeORM (src/orm.ts); search stays raw SQL (FTS5). */
|
|
6221
6150
|
var cmds_exports$2 = /* @__PURE__ */ require_rolldown_runtime.__exportAll({ run: () => run$8 });
|
|
6222
6151
|
init_fmt();
|
|
6223
|
-
init_text();
|
|
6152
|
+
require_text.init_text();
|
|
6224
6153
|
init_orm();
|
|
6225
6154
|
init_writes();
|
|
6226
6155
|
init_entities$1();
|
|
@@ -6261,7 +6190,7 @@ function run$8(env, action, rest, args) {
|
|
|
6261
6190
|
return 2;
|
|
6262
6191
|
}
|
|
6263
6192
|
const engine = String(args.flags.engine || "");
|
|
6264
|
-
return runWrite(env, (ds) => queryAdd(ds, project.id, text, engine, force), (r) => `query registered: ${r.id} ${clip(text, 60)}`);
|
|
6193
|
+
return runWrite(env, (ds) => queryAdd(ds, project.id, text, engine, force), (r) => `query registered: ${r.id} ${require_text.clip(text, 60)}`);
|
|
6265
6194
|
}
|
|
6266
6195
|
if (subAction === "attach") {
|
|
6267
6196
|
if (!rest[1] || !rest[2]) {
|
|
@@ -6271,7 +6200,7 @@ function run$8(env, action, rest, args) {
|
|
|
6271
6200
|
const note = String(args.flags.note || "");
|
|
6272
6201
|
return getOrm(env.db.path).then((ds) => queryAttach(ds, project.id, rest[1], rest[2], note)).then((r) => {
|
|
6273
6202
|
if (r.dup) out(ctx, paint(C.yellow, ` ! already attached: ${r.sourceId}`, ctx.color));
|
|
6274
|
-
else ok(ctx, `attached: ${clip(r.sourceTitle || r.sourceId, 40)} → "${clip(r.queryText, 40)}"`);
|
|
6203
|
+
else ok(ctx, `attached: ${require_text.clip(r.sourceTitle || r.sourceId, 40)} → "${require_text.clip(r.queryText, 40)}"`);
|
|
6275
6204
|
return 0;
|
|
6276
6205
|
}).catch((e) => {
|
|
6277
6206
|
bad(ctx, e?.message || String(e));
|
|
@@ -6357,7 +6286,7 @@ function run$8(env, action, rest, args) {
|
|
|
6357
6286
|
return 2;
|
|
6358
6287
|
}
|
|
6359
6288
|
if (url && !/^https?:\/\/|^file:\/\//.test(url)) {
|
|
6360
|
-
bad(ctx, `--url must be http(s):// or file:// (got: "${clip(url, 30)}")`);
|
|
6289
|
+
bad(ctx, `--url must be http(s):// or file:// (got: "${require_text.clip(url, 30)}")`);
|
|
6361
6290
|
return 2;
|
|
6362
6291
|
}
|
|
6363
6292
|
const spec = {
|
|
@@ -6373,10 +6302,10 @@ function run$8(env, action, rest, args) {
|
|
|
6373
6302
|
const qRef = String(args.flags.query || "");
|
|
6374
6303
|
return getOrm(env.db.path).then(async (ds) => {
|
|
6375
6304
|
const r = await sourceAdd(ds, project.id, spec);
|
|
6376
|
-
writeResult(ctx, r, (row) => `source added: ${row.id} ${clip(row.title, 60)}`);
|
|
6305
|
+
writeResult(ctx, r, (row) => `source added: ${row.id} ${require_text.clip(row.title, 60)}`);
|
|
6377
6306
|
if (qRef) {
|
|
6378
6307
|
const at = await queryAttach(ds, project.id, qRef, r.row.id);
|
|
6379
|
-
if (!ctx.json && !at.dup) out(ctx, paint(C.dim, ` attached to query: "${clip(at.queryText, 40)}"`, ctx.color));
|
|
6308
|
+
if (!ctx.json && !at.dup) out(ctx, paint(C.dim, ` attached to query: "${require_text.clip(at.queryText, 40)}"`, ctx.color));
|
|
6380
6309
|
}
|
|
6381
6310
|
return 0;
|
|
6382
6311
|
}).catch((e) => {
|
|
@@ -6419,7 +6348,7 @@ function run$8(env, action, rest, args) {
|
|
|
6419
6348
|
confidence: String(args.flags.confidence || configGet(env.db, "default_confidence")),
|
|
6420
6349
|
tags: String(args.flags.tags || (thin ? "needs_review" : ""))
|
|
6421
6350
|
});
|
|
6422
|
-
writeResult(ctx, r, (row) => `fetched: ${row.id} ${clip(title, 60)}`);
|
|
6351
|
+
writeResult(ctx, r, (row) => `fetched: ${row.id} ${require_text.clip(title, 60)}`);
|
|
6423
6352
|
if (!ctx.json) out(ctx, paint(C.dim, ` ${(text.length / 1e3).toFixed(1)}k chars text · ${metaDesc ? "meta description" : "no meta"}${thin ? " · thin content → tagged needs_review" : ""}`, ctx.color));
|
|
6424
6353
|
return 0;
|
|
6425
6354
|
}).catch((e) => {
|
|
@@ -6477,7 +6406,7 @@ function run$8(env, action, rest, args) {
|
|
|
6477
6406
|
}
|
|
6478
6407
|
table(ctx, store.sourceSearch(project.id, q).map((r) => ({
|
|
6479
6408
|
id: r.id,
|
|
6480
|
-
title: clip(r.title, 50),
|
|
6409
|
+
title: require_text.clip(r.title, 50),
|
|
6481
6410
|
rel: r.relevance,
|
|
6482
6411
|
conf: r.confidence,
|
|
6483
6412
|
score: typeof r.score === "number" ? r.score.toFixed(2) : "-"
|
|
@@ -6531,7 +6460,7 @@ function run$8(env, action, rest, args) {
|
|
|
6531
6460
|
}
|
|
6532
6461
|
const note = String(args.flags.note || "");
|
|
6533
6462
|
const locator = String(args.flags.locator || "");
|
|
6534
|
-
return runWrite(env, (ds) => evidenceAdd(ds, project.id, sourceId, quote, note, locator, force), (r) => `evidence added: ${r.id} ${clip(quote, 50)}`);
|
|
6463
|
+
return runWrite(env, (ds) => evidenceAdd(ds, project.id, sourceId, quote, note, locator, force), (r) => `evidence added: ${r.id} ${require_text.clip(quote, 50)}`);
|
|
6535
6464
|
}
|
|
6536
6465
|
if (action === "evidence" && subAction === "assess") {
|
|
6537
6466
|
const id = rest[1];
|
|
@@ -6564,7 +6493,7 @@ function run$8(env, action, rest, args) {
|
|
|
6564
6493
|
else {
|
|
6565
6494
|
head(ctx, `evidence assess: ${id}`);
|
|
6566
6495
|
show(ctx, {
|
|
6567
|
-
引文: clip(ev.quote, 60),
|
|
6496
|
+
引文: require_text.clip(ev.quote, 60),
|
|
6568
6497
|
来源: ev.source_title || "-",
|
|
6569
6498
|
模型评分: result.quality_score !== null ? `${result.quality_score}/5` : "离线",
|
|
6570
6499
|
可靠性: result.reliability
|
|
@@ -6586,7 +6515,7 @@ function run$8(env, action, rest, args) {
|
|
|
6586
6515
|
id: e.id,
|
|
6587
6516
|
source: e.source?.title ?? "",
|
|
6588
6517
|
locator: e.locator,
|
|
6589
|
-
quote: clip(e.quote, 60),
|
|
6518
|
+
quote: require_text.clip(e.quote, 60),
|
|
6590
6519
|
used_by: e.claimEvidence?.length ?? 0
|
|
6591
6520
|
}));
|
|
6592
6521
|
table(ctx, rows, [
|
|
@@ -6622,7 +6551,7 @@ function run$8(env, action, rest, args) {
|
|
|
6622
6551
|
return 2;
|
|
6623
6552
|
}
|
|
6624
6553
|
const confidence = String(args.flags.confidence || configGet(env.db, "default_confidence"));
|
|
6625
|
-
return runWrite(env, (ds) => claimAdd(ds, project.id, text, confidence, force), (r) => `claim added: ${r.id} ${clip(text, 60)}`);
|
|
6554
|
+
return runWrite(env, (ds) => claimAdd(ds, project.id, text, confidence, force), (r) => `claim added: ${r.id} ${require_text.clip(text, 60)}`);
|
|
6626
6555
|
}
|
|
6627
6556
|
if (subAction === "link") {
|
|
6628
6557
|
if (!rest[1] || !rest[2]) {
|
|
@@ -6744,7 +6673,7 @@ function run$8(env, action, rest, args) {
|
|
|
6744
6673
|
else {
|
|
6745
6674
|
head(ctx, `claim evaluate: ${id}`);
|
|
6746
6675
|
show(ctx, {
|
|
6747
|
-
断言: clip(claim.text, 60),
|
|
6676
|
+
断言: require_text.clip(claim.text, 60),
|
|
6748
6677
|
当前状态: claim.status,
|
|
6749
6678
|
当前置信度: claim.confidence,
|
|
6750
6679
|
模型评分: result.confidence_score !== null ? `${result.confidence_score}/5` : "离线",
|
|
@@ -6763,7 +6692,7 @@ function run$8(env, action, rest, args) {
|
|
|
6763
6692
|
order: { created: "ASC" }
|
|
6764
6693
|
})).map((c) => ({
|
|
6765
6694
|
id: c.id,
|
|
6766
|
-
text: clip(c.text, 60),
|
|
6695
|
+
text: require_text.clip(c.text, 60),
|
|
6767
6696
|
status: c.status,
|
|
6768
6697
|
confidence: c.confidence,
|
|
6769
6698
|
sup: (c.claimEvidence ?? []).filter((ce) => ce.stance === "supports").length,
|
|
@@ -6936,7 +6865,7 @@ function run$7(env, action, rest, args) {
|
|
|
6936
6865
|
* Store until their own migration batch. */
|
|
6937
6866
|
var produce_cmds_exports = /* @__PURE__ */ require_rolldown_runtime.__exportAll({ run: () => run$6 });
|
|
6938
6867
|
init_fmt();
|
|
6939
|
-
init_text();
|
|
6868
|
+
require_text.init_text();
|
|
6940
6869
|
init_orm();
|
|
6941
6870
|
init_writes();
|
|
6942
6871
|
function run$6(env, action, rest, args) {
|
|
@@ -6983,7 +6912,7 @@ function run$6(env, action, rest, args) {
|
|
|
6983
6912
|
lines.push("", "## 证据基础", "");
|
|
6984
6913
|
const ev = store.evidenceList(pid);
|
|
6985
6914
|
if (!ev.length) lines.push("_(尚无 evidence)_", "");
|
|
6986
|
-
ev.forEach((e, i) => lines.push(`- [${i + 1}] ${e.source}:${clip(e.quote, 80)}`));
|
|
6915
|
+
ev.forEach((e, i) => lines.push(`- [${i + 1}] ${e.source}:${require_text.clip(e.quote, 80)}`));
|
|
6987
6916
|
const content = lines.join("\n");
|
|
6988
6917
|
return getOrm(env.db.path).then((ds) => artifactAdd(ds, pid, "outline", `${project.name} outline`, content)).then((r) => {
|
|
6989
6918
|
if (ctx.json) console.log(JSON.stringify(r.row, null, 2));
|
|
@@ -7229,9 +7158,9 @@ function run$6(env, action, rest, args) {
|
|
|
7229
7158
|
//#endregion
|
|
7230
7159
|
//#region packages/techtree/model/src/writes.ts
|
|
7231
7160
|
init_db();
|
|
7232
|
-
init_text();
|
|
7161
|
+
require_text.init_text();
|
|
7233
7162
|
async function markDirty(mgr, treeId) {
|
|
7234
|
-
await mgr.query(`INSERT INTO node_index(tree_id,built_at,dirty) VALUES(?,?,1) ON CONFLICT(tree_id) DO UPDATE SET dirty=1`, [treeId, nowIso()]);
|
|
7163
|
+
await mgr.query(`INSERT INTO node_index(tree_id,built_at,dirty) VALUES(?,?,1) ON CONFLICT(tree_id) DO UPDATE SET dirty=1`, [treeId, require_text.nowIso()]);
|
|
7235
7164
|
}
|
|
7236
7165
|
/** R10.1 (0.30): tree-domain audit trail — overturns the 0.12 "no events"
|
|
7237
7166
|
* exception. Same shape as the research-domain logEvent (raw SQL here since
|
|
@@ -7243,8 +7172,8 @@ async function logEvent(mgr, kind, entityId, payload, level = "info") {
|
|
|
7243
7172
|
run
|
|
7244
7173
|
}) : JSON.stringify(payload ?? {});
|
|
7245
7174
|
await mgr.query(`INSERT INTO events(id,ts,actor,kind,entity,entity_id,payload,level) VALUES(?,?,?,?,?,?,?,?)`, [
|
|
7246
|
-
shortId([kind, entityId], 12),
|
|
7247
|
-
nowIso(),
|
|
7175
|
+
require_text.shortId([kind, entityId], 12),
|
|
7176
|
+
require_text.nowIso(),
|
|
7248
7177
|
"cli",
|
|
7249
7178
|
kind,
|
|
7250
7179
|
"node",
|
|
@@ -7373,7 +7302,7 @@ async function buildIndex(mgr, treeId) {
|
|
|
7373
7302
|
JSON.stringify(topo),
|
|
7374
7303
|
JSON.stringify(tiers),
|
|
7375
7304
|
JSON.stringify(inDegree),
|
|
7376
|
-
nowIso()
|
|
7305
|
+
require_text.nowIso()
|
|
7377
7306
|
]);
|
|
7378
7307
|
return {
|
|
7379
7308
|
topo,
|
|
@@ -7388,13 +7317,13 @@ async function treeCreate(ds, name, projectId = "", note = "") {
|
|
|
7388
7317
|
...existing[0],
|
|
7389
7318
|
duplicate: true
|
|
7390
7319
|
};
|
|
7391
|
-
const id = shortId(["tree", name], 10);
|
|
7320
|
+
const id = require_text.shortId(["tree", name], 10);
|
|
7392
7321
|
await mgr.query(`INSERT INTO trees(id,project_id,name,note,created) VALUES(?,?,?,?,?)`, [
|
|
7393
7322
|
id,
|
|
7394
7323
|
projectId || null,
|
|
7395
7324
|
name,
|
|
7396
7325
|
note,
|
|
7397
|
-
nowIso()
|
|
7326
|
+
require_text.nowIso()
|
|
7398
7327
|
]);
|
|
7399
7328
|
await markDirty(mgr, id);
|
|
7400
7329
|
return (await mgr.query(`SELECT * FROM trees WHERE id=?`, [id]))[0];
|
|
@@ -7407,7 +7336,7 @@ async function nodeAdd(ds, treeId, o) {
|
|
|
7407
7336
|
row: ex[0],
|
|
7408
7337
|
created: false
|
|
7409
7338
|
};
|
|
7410
|
-
const id = shortId([
|
|
7339
|
+
const id = require_text.shortId([
|
|
7411
7340
|
"node",
|
|
7412
7341
|
treeId,
|
|
7413
7342
|
o.key
|
|
@@ -7424,14 +7353,14 @@ async function nodeAdd(ds, treeId, o) {
|
|
|
7424
7353
|
o.cost_unit || "",
|
|
7425
7354
|
o.payload || "",
|
|
7426
7355
|
o.tags || "",
|
|
7427
|
-
nowIso()
|
|
7356
|
+
require_text.nowIso()
|
|
7428
7357
|
]);
|
|
7429
7358
|
await mgr.query(`INSERT INTO nodes_fts(id,key,name,tags,ngram) VALUES(?,?,?,?,?)`, [
|
|
7430
7359
|
id,
|
|
7431
7360
|
o.key,
|
|
7432
7361
|
name,
|
|
7433
7362
|
o.tags || "",
|
|
7434
|
-
ngram(`${o.key} ${name} ${o.tags || ""}`)
|
|
7363
|
+
require_text.ngram(`${o.key} ${name} ${o.tags || ""}`)
|
|
7435
7364
|
]);
|
|
7436
7365
|
await markDirty(mgr, treeId);
|
|
7437
7366
|
await logEvent(mgr, "node.add", id, {
|
|
@@ -7492,7 +7421,7 @@ async function link(ds, treeId, parentKey, childKey, o = {}) {
|
|
|
7492
7421
|
rel
|
|
7493
7422
|
]);
|
|
7494
7423
|
const duplicate = before.length > 0;
|
|
7495
|
-
const id = duplicate ? before[0].id : shortId([
|
|
7424
|
+
const id = duplicate ? before[0].id : require_text.shortId([
|
|
7496
7425
|
"edge",
|
|
7497
7426
|
p[0].id,
|
|
7498
7427
|
c[0].id,
|
|
@@ -7513,7 +7442,7 @@ async function link(ds, treeId, parentKey, childKey, o = {}) {
|
|
|
7513
7442
|
o.min_level ?? 1,
|
|
7514
7443
|
o.weight ?? 1,
|
|
7515
7444
|
o.note || "",
|
|
7516
|
-
nowIso()
|
|
7445
|
+
require_text.nowIso()
|
|
7517
7446
|
]);
|
|
7518
7447
|
await rebuildClosure(mgr, treeId);
|
|
7519
7448
|
await logEvent(mgr, "node.link", id, {
|
|
@@ -7574,7 +7503,7 @@ async function condAdd(ds, treeId, keyOrId, o) {
|
|
|
7574
7503
|
if (!n.length) throw new Error(`node not found: ${keyOrId}`);
|
|
7575
7504
|
const kind = o.kind || "flag";
|
|
7576
7505
|
if (!COND_KINDS.includes(kind)) throw new Error(`kind must be one of ${COND_KINDS.join("|")}`);
|
|
7577
|
-
const id = shortId([
|
|
7506
|
+
const id = require_text.shortId([
|
|
7578
7507
|
"cond",
|
|
7579
7508
|
n[0].id,
|
|
7580
7509
|
o.name
|
|
@@ -7621,7 +7550,7 @@ async function stateSet(ds, treeId, keyOrId, status, context = "default", level
|
|
|
7621
7550
|
status,
|
|
7622
7551
|
level,
|
|
7623
7552
|
status === "unlocked" ? 1 : 0,
|
|
7624
|
-
nowIso()
|
|
7553
|
+
require_text.nowIso()
|
|
7625
7554
|
]);
|
|
7626
7555
|
await logEvent(mgr, status === "unlocked" ? "node.unlock" : "node.lock", n[0].id, {
|
|
7627
7556
|
tree: treeId,
|
|
@@ -7714,13 +7643,13 @@ async function importTree(ds, spec, opts = {}) {
|
|
|
7714
7643
|
let tid;
|
|
7715
7644
|
if (existing.length) tid = existing[0].id;
|
|
7716
7645
|
else {
|
|
7717
|
-
tid = shortId(["tree", name], 10);
|
|
7646
|
+
tid = require_text.shortId(["tree", name], 10);
|
|
7718
7647
|
await mgr.query(`INSERT INTO trees(id,project_id,name,note,created) VALUES(?,?,?,?,?)`, [
|
|
7719
7648
|
tid,
|
|
7720
7649
|
null,
|
|
7721
7650
|
name,
|
|
7722
7651
|
String(spec.tree?.note || ""),
|
|
7723
|
-
nowIso()
|
|
7652
|
+
require_text.nowIso()
|
|
7724
7653
|
]);
|
|
7725
7654
|
}
|
|
7726
7655
|
const nodeId = /* @__PURE__ */ new Map();
|
|
@@ -7730,7 +7659,7 @@ async function importTree(ds, spec, opts = {}) {
|
|
|
7730
7659
|
nodeId.set(String(n.key), ex[0].id);
|
|
7731
7660
|
continue;
|
|
7732
7661
|
}
|
|
7733
|
-
const id = shortId([
|
|
7662
|
+
const id = require_text.shortId([
|
|
7734
7663
|
"node",
|
|
7735
7664
|
tid,
|
|
7736
7665
|
String(n.key)
|
|
@@ -7748,14 +7677,14 @@ async function importTree(ds, spec, opts = {}) {
|
|
|
7748
7677
|
n.cost_unit === void 0 ? "" : String(n.cost_unit),
|
|
7749
7678
|
n.payload === void 0 || n.payload === null ? "" : typeof n.payload === "object" ? JSON.stringify(n.payload) : String(n.payload),
|
|
7750
7679
|
n.tags === void 0 ? "" : String(n.tags),
|
|
7751
|
-
nowIso()
|
|
7680
|
+
require_text.nowIso()
|
|
7752
7681
|
]);
|
|
7753
7682
|
await mgr.query(`INSERT INTO nodes_fts(id,key,name,tags,ngram) VALUES(?,?,?,?,?)`, [
|
|
7754
7683
|
id,
|
|
7755
7684
|
String(n.key),
|
|
7756
7685
|
nm,
|
|
7757
7686
|
n.tags === void 0 ? "" : String(n.tags),
|
|
7758
|
-
ngram(`${n.key} ${nm} ${n.tags || ""}`)
|
|
7687
|
+
require_text.ngram(`${n.key} ${nm} ${n.tags || ""}`)
|
|
7759
7688
|
]);
|
|
7760
7689
|
}
|
|
7761
7690
|
for (const e of edges) {
|
|
@@ -7766,7 +7695,7 @@ async function importTree(ds, spec, opts = {}) {
|
|
|
7766
7695
|
ON CONFLICT(parent_id,child_id,rel) DO UPDATE SET
|
|
7767
7696
|
mode=excluded.mode, required=excluded.required, min_level=excluded.min_level,
|
|
7768
7697
|
weight=excluded.weight, note=excluded.note`, [
|
|
7769
|
-
shortId([
|
|
7698
|
+
require_text.shortId([
|
|
7770
7699
|
"edge",
|
|
7771
7700
|
tid,
|
|
7772
7701
|
pid,
|
|
@@ -7782,7 +7711,7 @@ async function importTree(ds, spec, opts = {}) {
|
|
|
7782
7711
|
Number(e.min_level ?? 1),
|
|
7783
7712
|
Number(e.weight ?? 1),
|
|
7784
7713
|
String(e.note || ""),
|
|
7785
|
-
nowIso()
|
|
7714
|
+
require_text.nowIso()
|
|
7786
7715
|
]);
|
|
7787
7716
|
}
|
|
7788
7717
|
for (const c of conds) {
|
|
@@ -7790,7 +7719,7 @@ async function importTree(ds, spec, opts = {}) {
|
|
|
7790
7719
|
await mgr.query(`DELETE FROM node_conditions WHERE node_id=? AND name=?`, [nid, String(c.name)]);
|
|
7791
7720
|
await mgr.query(`INSERT INTO node_conditions(id,node_id,name,kind,expr,op,value,required,effect,weight,note)
|
|
7792
7721
|
VALUES(?,?,?,?,?,?,?,?,?,?,?)`, [
|
|
7793
|
-
shortId([
|
|
7722
|
+
require_text.shortId([
|
|
7794
7723
|
"cond",
|
|
7795
7724
|
tid,
|
|
7796
7725
|
nid,
|
|
@@ -7839,7 +7768,7 @@ var cmds_exports$1 = /* @__PURE__ */ require_rolldown_runtime.__exportAll({ run:
|
|
|
7839
7768
|
init_fmt();
|
|
7840
7769
|
init_orm();
|
|
7841
7770
|
init_eval();
|
|
7842
|
-
init_text();
|
|
7771
|
+
require_text.init_text();
|
|
7843
7772
|
function run$5(env, action, rest, args) {
|
|
7844
7773
|
const { ctx, db } = env;
|
|
7845
7774
|
const trees = new TreeStore(db);
|
|
@@ -8193,12 +8122,12 @@ function run$5(env, action, rest, args) {
|
|
|
8193
8122
|
try {
|
|
8194
8123
|
const run = process.env.YGL_RUN_ID || "";
|
|
8195
8124
|
db.run("INSERT INTO events(id,ts,actor,kind,entity,entity_id,payload,level) VALUES(?,?,?,?,?,?,?,'info')", [
|
|
8196
|
-
shortId([
|
|
8125
|
+
require_text.shortId([
|
|
8197
8126
|
"eval.gate",
|
|
8198
8127
|
"node",
|
|
8199
8128
|
key
|
|
8200
8129
|
], 12),
|
|
8201
|
-
nowIso(),
|
|
8130
|
+
require_text.nowIso(),
|
|
8202
8131
|
"cli",
|
|
8203
8132
|
"eval.gate",
|
|
8204
8133
|
"node",
|
|
@@ -8376,12 +8305,12 @@ function run$5(env, action, rest, args) {
|
|
|
8376
8305
|
try {
|
|
8377
8306
|
const run = process.env.YGL_RUN_ID || "";
|
|
8378
8307
|
db.run("INSERT INTO events(id,ts,actor,kind,entity,entity_id,payload,level) VALUES(?,?,?,?,?,?,?,'info')", [
|
|
8379
|
-
shortId([
|
|
8308
|
+
require_text.shortId([
|
|
8380
8309
|
"eval.ready",
|
|
8381
8310
|
"tree",
|
|
8382
8311
|
tid
|
|
8383
8312
|
], 12),
|
|
8384
|
-
nowIso(),
|
|
8313
|
+
require_text.nowIso(),
|
|
8385
8314
|
"cli",
|
|
8386
8315
|
"eval.ready",
|
|
8387
8316
|
"tree",
|
|
@@ -8684,7 +8613,7 @@ function parseState(args) {
|
|
|
8684
8613
|
* Writes run on the TypeORM write service (src/writes.ts). */
|
|
8685
8614
|
var skill_cmds_exports = /* @__PURE__ */ require_rolldown_runtime.__exportAll({ run: () => run$4 });
|
|
8686
8615
|
init_fmt();
|
|
8687
|
-
init_text();
|
|
8616
|
+
require_text.init_text();
|
|
8688
8617
|
init_orm();
|
|
8689
8618
|
init_writes();
|
|
8690
8619
|
function run$4(env, action, rest, args) {
|
|
@@ -8700,7 +8629,8 @@ function run$4(env, action, rest, args) {
|
|
|
8700
8629
|
switch (action) {
|
|
8701
8630
|
case "import": {
|
|
8702
8631
|
if (!need(name, "file")) return 2;
|
|
8703
|
-
const
|
|
8632
|
+
const raw = node_fs.readFileSync(name, "utf8");
|
|
8633
|
+
const { meta, body } = require_text.parseFrontmatter(raw);
|
|
8704
8634
|
const spec = {
|
|
8705
8635
|
name: meta.name || node_path.basename(name, ".md"),
|
|
8706
8636
|
description: meta.description || "",
|
|
@@ -8825,7 +8755,23 @@ function run$4(env, action, rest, args) {
|
|
|
8825
8755
|
return 0;
|
|
8826
8756
|
case "link": {
|
|
8827
8757
|
const os = require("node:os");
|
|
8828
|
-
const
|
|
8758
|
+
const globalFlag = args?.flags?.global === true;
|
|
8759
|
+
const aiName = String(args?.flags?.ai || "").toLowerCase();
|
|
8760
|
+
const customTo = String(args?.flags?.to || "");
|
|
8761
|
+
const AI_SKILL_DIRS = {
|
|
8762
|
+
pi: () => node_path.join(os.homedir(), ".pi", "agent", "skills"),
|
|
8763
|
+
claude: () => node_path.join(os.homedir(), ".claude", "skills"),
|
|
8764
|
+
cursor: () => node_path.join(os.homedir(), ".cursor", "skills"),
|
|
8765
|
+
windsurf: () => node_path.join(os.homedir(), ".windsurf", "skills")
|
|
8766
|
+
};
|
|
8767
|
+
let targetDir;
|
|
8768
|
+
if (customTo) targetDir = node_path.resolve(customTo);
|
|
8769
|
+
else if (aiName && AI_SKILL_DIRS[aiName]) targetDir = AI_SKILL_DIRS[aiName]();
|
|
8770
|
+
else if (aiName && aiName !== "custom") {
|
|
8771
|
+
bad(ctx, `unknown AI agent: ${aiName}`);
|
|
8772
|
+
out(ctx, ` supported: ${Object.keys(AI_SKILL_DIRS).join(", ")} | custom (with --to <path>)`);
|
|
8773
|
+
return 2;
|
|
8774
|
+
} else targetDir = globalFlag ? node_path.join(os.homedir(), ".agents", "skills") : node_path.join(process.cwd(), ".agents", "skills");
|
|
8829
8775
|
let skillsDir = null;
|
|
8830
8776
|
for (let dir = process.cwd(), i = 0; i < 6; i++, dir = node_path.dirname(dir)) {
|
|
8831
8777
|
const candidate = node_path.join(dir, "skills");
|
|
@@ -9002,7 +8948,7 @@ function wrap(text, indent = 4) {
|
|
|
9002
8948
|
* Writes (add/ingest) run on the TypeORM write service (src/writes.ts). */
|
|
9003
8949
|
var cmds_exports = /* @__PURE__ */ require_rolldown_runtime.__exportAll({ run: () => run$3 });
|
|
9004
8950
|
init_fmt();
|
|
9005
|
-
init_text();
|
|
8951
|
+
require_text.init_text();
|
|
9006
8952
|
init_orm();
|
|
9007
8953
|
init_writes();
|
|
9008
8954
|
function run$3(env, action, rest, args) {
|
|
@@ -9035,7 +8981,7 @@ function run$3(env, action, rest, args) {
|
|
|
9035
8981
|
confidence: String(args.flags.confidence || configGet(env.db, "default_confidence")),
|
|
9036
8982
|
force
|
|
9037
8983
|
})).then((r) => {
|
|
9038
|
-
writeResult(ctx, r, (row) => `note stored: ${row.id} ${clip(title, 50)}`);
|
|
8984
|
+
writeResult(ctx, r, (row) => `note stored: ${row.id} ${require_text.clip(title, 50)}`);
|
|
9039
8985
|
return 0;
|
|
9040
8986
|
}).catch((e) => {
|
|
9041
8987
|
bad(ctx, e?.message || String(e));
|
|
@@ -9061,7 +9007,7 @@ function run$3(env, action, rest, args) {
|
|
|
9061
9007
|
const orig = idToRaw.get(rr.id);
|
|
9062
9008
|
return {
|
|
9063
9009
|
id: rr.id,
|
|
9064
|
-
title: clip(orig.title, 42),
|
|
9010
|
+
title: require_text.clip(orig.title, 42),
|
|
9065
9011
|
semantic: rr.semantic_relevance !== null ? rr.semantic_relevance.toFixed(2) : "离线",
|
|
9066
9012
|
orig_rank: rr.original_rank,
|
|
9067
9013
|
tags: orig.tags || "-",
|
|
@@ -9093,7 +9039,7 @@ function run$3(env, action, rest, args) {
|
|
|
9093
9039
|
}
|
|
9094
9040
|
table(ctx, raw.map((r) => ({
|
|
9095
9041
|
id: r.id,
|
|
9096
|
-
title: clip(r.title, 46),
|
|
9042
|
+
title: require_text.clip(r.title, 46),
|
|
9097
9043
|
tags: r.tags || "-",
|
|
9098
9044
|
conf: r.confidence,
|
|
9099
9045
|
reuse: r.reuse,
|
|
@@ -9194,7 +9140,7 @@ function run$3(env, action, rest, args) {
|
|
|
9194
9140
|
}
|
|
9195
9141
|
const forceKb = args.flags.force === true || args.flags.force === "true";
|
|
9196
9142
|
return getOrm(env.db.path).then((ds) => kbIngestArtifact(ds, rest[0], forceKb)).then((r) => {
|
|
9197
|
-
writeResult(ctx, r, (row) => `artifact ingested into kb: ${row.id} ${clip(row.title, 50)}`);
|
|
9143
|
+
writeResult(ctx, r, (row) => `artifact ingested into kb: ${row.id} ${require_text.clip(row.title, 50)}`);
|
|
9198
9144
|
return 0;
|
|
9199
9145
|
}).catch((e) => {
|
|
9200
9146
|
bad(ctx, e?.message || String(e));
|
|
@@ -9220,7 +9166,7 @@ function run$3(env, action, rest, args) {
|
|
|
9220
9166
|
origin: `kb:${note.id}`
|
|
9221
9167
|
})).then((s) => {
|
|
9222
9168
|
ok(ctx, `promoted to skill: ${s.name}`);
|
|
9223
|
-
out(ctx, paint(C.dim, ` L1: ${clip(String(s.description), 100)}`, ctx.color));
|
|
9169
|
+
out(ctx, paint(C.dim, ` L1: ${require_text.clip(String(s.description), 100)}`, ctx.color));
|
|
9224
9170
|
return 0;
|
|
9225
9171
|
}).catch((e) => {
|
|
9226
9172
|
bad(ctx, e?.message || String(e));
|
|
@@ -9270,7 +9216,8 @@ function run$3(env, action, rest, args) {
|
|
|
9270
9216
|
return 1;
|
|
9271
9217
|
}
|
|
9272
9218
|
const items = importable.map((f) => {
|
|
9273
|
-
const
|
|
9219
|
+
const raw = node_fs.readFileSync(f, "utf8");
|
|
9220
|
+
const { meta, body } = require_text.parseFrontmatter(raw);
|
|
9274
9221
|
const heading = /^#\s+(.+)\s*$/m.exec(body)?.[1]?.trim();
|
|
9275
9222
|
return {
|
|
9276
9223
|
title: meta.title || meta.name || heading || node_path.basename(f, ".md"),
|
|
@@ -9315,7 +9262,7 @@ var rels_exports = /* @__PURE__ */ require_rolldown_runtime.__exportAll({
|
|
|
9315
9262
|
run: () => run$2
|
|
9316
9263
|
});
|
|
9317
9264
|
init_fmt();
|
|
9318
|
-
init_text();
|
|
9265
|
+
require_text.init_text();
|
|
9319
9266
|
init_orm();
|
|
9320
9267
|
const REL_TYPES = [
|
|
9321
9268
|
"node",
|
|
@@ -9448,7 +9395,7 @@ async function relAdd(env, srcRef, dstRef, rel = "related") {
|
|
|
9448
9395
|
row: (await mgr.query(`SELECT * FROM relations WHERE id=?`, [ex[0].id]))[0],
|
|
9449
9396
|
duplicate: true
|
|
9450
9397
|
};
|
|
9451
|
-
const id = shortId([
|
|
9398
|
+
const id = require_text.shortId([
|
|
9452
9399
|
"rel",
|
|
9453
9400
|
src.id,
|
|
9454
9401
|
dst.id,
|
|
@@ -9461,15 +9408,15 @@ async function relAdd(env, srcRef, dstRef, rel = "related") {
|
|
|
9461
9408
|
dst.type,
|
|
9462
9409
|
dst.id,
|
|
9463
9410
|
rel,
|
|
9464
|
-
nowIso()
|
|
9411
|
+
require_text.nowIso()
|
|
9465
9412
|
]);
|
|
9466
9413
|
await mgr.query(`INSERT INTO events(id,ts,actor,kind,entity,entity_id,payload) VALUES(?,?,?,?,?,?,?)`, [
|
|
9467
|
-
shortId([
|
|
9414
|
+
require_text.shortId([
|
|
9468
9415
|
"ev",
|
|
9469
9416
|
"rel.add",
|
|
9470
9417
|
id
|
|
9471
9418
|
], 12),
|
|
9472
|
-
nowIso(),
|
|
9419
|
+
require_text.nowIso(),
|
|
9473
9420
|
"cli",
|
|
9474
9421
|
"rel.add",
|
|
9475
9422
|
"relation",
|
|
@@ -11113,6 +11060,20 @@ async function main(argv) {
|
|
|
11113
11060
|
});
|
|
11114
11061
|
} catch (e) {
|
|
11115
11062
|
if (e instanceof StartupError) {
|
|
11063
|
+
if (group === "plugin") {
|
|
11064
|
+
const pluginCmds = await Promise.resolve().then(() => plugin_exports);
|
|
11065
|
+
const { dbPath } = await Promise.resolve().then(() => (init_db(), db_exports));
|
|
11066
|
+
const env2 = {
|
|
11067
|
+
home,
|
|
11068
|
+
dbFile: dbPath(home),
|
|
11069
|
+
ctx,
|
|
11070
|
+
db: null,
|
|
11071
|
+
store: null,
|
|
11072
|
+
cordis: null
|
|
11073
|
+
};
|
|
11074
|
+
out(ctx, paint(C.yellow, " ! degraded mode: user plugins failed to load — plugin commands only", ctx.color));
|
|
11075
|
+
return pluginCmds.runPluginCommand(env2, action || "list", args._.slice(2), args);
|
|
11076
|
+
}
|
|
11116
11077
|
reportStartupFailure(e, home, VERSION);
|
|
11117
11078
|
return 1;
|
|
11118
11079
|
}
|