clitrigger 0.1.14 → 0.1.16
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/README.md +15 -4
- package/README_KR.md +15 -4
- package/bin/clitrigger.js +41 -4
- package/dist/client/assets/index-BldpDcSD.js +686 -0
- package/dist/client/assets/{index-BDEcscfu.css → index-CRSNebDI.css} +1 -1
- package/dist/client/index.html +2 -2
- package/dist/server/db/app-settings.d.ts +3 -0
- package/dist/server/db/app-settings.d.ts.map +1 -0
- package/dist/server/db/app-settings.js +16 -0
- package/dist/server/db/app-settings.js.map +1 -0
- package/dist/server/db/queries.d.ts +27 -3
- package/dist/server/db/queries.d.ts.map +1 -1
- package/dist/server/db/queries.js +25 -5
- package/dist/server/db/queries.js.map +1 -1
- package/dist/server/db/schema.d.ts.map +1 -1
- package/dist/server/db/schema.js +23 -0
- package/dist/server/db/schema.js.map +1 -1
- package/dist/server/index.d.ts.map +1 -1
- package/dist/server/index.js +4 -2
- package/dist/server/index.js.map +1 -1
- package/dist/server/routes/discussions.d.ts.map +1 -1
- package/dist/server/routes/discussions.js +1 -1
- package/dist/server/routes/discussions.js.map +1 -1
- package/dist/server/routes/memory.d.ts.map +1 -1
- package/dist/server/routes/memory.js +333 -0
- package/dist/server/routes/memory.js.map +1 -1
- package/dist/server/routes/sessions.d.ts.map +1 -1
- package/dist/server/routes/sessions.js +102 -3
- package/dist/server/routes/sessions.js.map +1 -1
- package/dist/server/routes/todos.js +2 -2
- package/dist/server/routes/todos.js.map +1 -1
- package/dist/server/routes/tunnel.d.ts.map +1 -1
- package/dist/server/routes/tunnel.js +37 -2
- package/dist/server/routes/tunnel.js.map +1 -1
- package/dist/server/services/discussion-orchestrator.d.ts.map +1 -1
- package/dist/server/services/discussion-orchestrator.js +2 -1
- package/dist/server/services/discussion-orchestrator.js.map +1 -1
- package/dist/server/services/memory-ingest.d.ts +4 -0
- package/dist/server/services/memory-ingest.d.ts.map +1 -1
- package/dist/server/services/memory-ingest.js +184 -21
- package/dist/server/services/memory-ingest.js.map +1 -1
- package/dist/server/services/memory-inject-hook.d.ts +3 -1
- package/dist/server/services/memory-inject-hook.d.ts.map +1 -1
- package/dist/server/services/memory-inject-hook.js +23 -3
- package/dist/server/services/memory-inject-hook.js.map +1 -1
- package/dist/server/services/memory-injector.d.ts +1 -1
- package/dist/server/services/memory-injector.d.ts.map +1 -1
- package/dist/server/services/memory-injector.js +18 -2
- package/dist/server/services/memory-injector.js.map +1 -1
- package/dist/server/services/memory-retriever.d.ts +16 -0
- package/dist/server/services/memory-retriever.d.ts.map +1 -0
- package/dist/server/services/memory-retriever.js +170 -0
- package/dist/server/services/memory-retriever.js.map +1 -0
- package/dist/server/services/orchestrator.d.ts.map +1 -1
- package/dist/server/services/orchestrator.js +2 -1
- package/dist/server/services/orchestrator.js.map +1 -1
- package/dist/server/services/session-manager.d.ts +22 -0
- package/dist/server/services/session-manager.d.ts.map +1 -1
- package/dist/server/services/session-manager.js +115 -3
- package/dist/server/services/session-manager.js.map +1 -1
- package/dist/server/services/tunnel-manager.d.ts +3 -1
- package/dist/server/services/tunnel-manager.d.ts.map +1 -1
- package/dist/server/services/tunnel-manager.js +18 -8
- package/dist/server/services/tunnel-manager.js.map +1 -1
- package/dist/server/services/wiki-exporter.d.ts +32 -0
- package/dist/server/services/wiki-exporter.d.ts.map +1 -0
- package/dist/server/services/wiki-exporter.js +430 -0
- package/dist/server/services/wiki-exporter.js.map +1 -0
- package/dist/server/services/wiki-index.d.ts +10 -0
- package/dist/server/services/wiki-index.d.ts.map +1 -0
- package/dist/server/services/wiki-index.js +100 -0
- package/dist/server/services/wiki-index.js.map +1 -0
- package/dist/server/websocket/index.d.ts.map +1 -1
- package/dist/server/websocket/index.js +8 -7
- package/dist/server/websocket/index.js.map +1 -1
- package/electron/main.cjs +224 -0
- package/electron/preload.cjs +3 -0
- package/package.json +58 -2
- package/dist/client/assets/index-uvmPjh-j.js +0 -654
|
@@ -0,0 +1,430 @@
|
|
|
1
|
+
import fs from 'fs';
|
|
2
|
+
import path from 'path';
|
|
3
|
+
import * as queries from '../db/queries.js';
|
|
4
|
+
import { regenerateIndexNode, WIKI_INDEX_TAG } from './wiki-index.js';
|
|
5
|
+
const WIKI_DIR_NAME = '.clitrigger';
|
|
6
|
+
const WIKI_SUBDIR = 'wiki';
|
|
7
|
+
const WIKI_SCHEMA_TAG = '__wiki_schema__';
|
|
8
|
+
const UNTAGGED_BUCKET = '_untagged';
|
|
9
|
+
const SCHEMA_FILENAME = '_schema.md';
|
|
10
|
+
const INDEX_FILENAME = '_index.md';
|
|
11
|
+
const MAX_SLUG_LEN = 60;
|
|
12
|
+
function isSchemaNode(n) {
|
|
13
|
+
if (!n.tags)
|
|
14
|
+
return false;
|
|
15
|
+
try {
|
|
16
|
+
const tags = JSON.parse(n.tags);
|
|
17
|
+
return Array.isArray(tags) && tags.includes(WIKI_SCHEMA_TAG);
|
|
18
|
+
}
|
|
19
|
+
catch {
|
|
20
|
+
return false;
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
function isIndexNode(n) {
|
|
24
|
+
if (!n.tags)
|
|
25
|
+
return false;
|
|
26
|
+
try {
|
|
27
|
+
const tags = JSON.parse(n.tags);
|
|
28
|
+
return Array.isArray(tags) && tags.includes(WIKI_INDEX_TAG);
|
|
29
|
+
}
|
|
30
|
+
catch {
|
|
31
|
+
return false;
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
function tagsArray(raw) {
|
|
35
|
+
if (!raw)
|
|
36
|
+
return [];
|
|
37
|
+
try {
|
|
38
|
+
const parsed = JSON.parse(raw);
|
|
39
|
+
return Array.isArray(parsed) ? parsed.map(String).map(s => s.trim()).filter(Boolean) : [];
|
|
40
|
+
}
|
|
41
|
+
catch {
|
|
42
|
+
return [];
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
function slugify(input) {
|
|
46
|
+
if (!input)
|
|
47
|
+
return 'untitled';
|
|
48
|
+
const cleaned = input
|
|
49
|
+
.replace(/[\\/:*?"<>|]/g, '')
|
|
50
|
+
.replace(/\s+/g, '-')
|
|
51
|
+
.replace(/-+/g, '-')
|
|
52
|
+
.replace(/^[-.]+|[-.]+$/g, '')
|
|
53
|
+
.toLowerCase()
|
|
54
|
+
.slice(0, MAX_SLUG_LEN);
|
|
55
|
+
return cleaned || 'untitled';
|
|
56
|
+
}
|
|
57
|
+
function bucketForNode(n) {
|
|
58
|
+
if (isSchemaNode(n) || isIndexNode(n))
|
|
59
|
+
return ''; // root
|
|
60
|
+
const tags = tagsArray(n.tags).filter(t => t !== WIKI_SCHEMA_TAG && t !== WIKI_INDEX_TAG);
|
|
61
|
+
if (tags.length === 0)
|
|
62
|
+
return UNTAGGED_BUCKET;
|
|
63
|
+
return slugify(tags[0]) || UNTAGGED_BUCKET;
|
|
64
|
+
}
|
|
65
|
+
function filenameForNode(n) {
|
|
66
|
+
if (isSchemaNode(n))
|
|
67
|
+
return SCHEMA_FILENAME;
|
|
68
|
+
if (isIndexNode(n))
|
|
69
|
+
return INDEX_FILENAME;
|
|
70
|
+
return `${slugify(n.title)}.md`;
|
|
71
|
+
}
|
|
72
|
+
function escapeYamlString(s) {
|
|
73
|
+
// Use double-quoted YAML strings; escape backslash and double-quote.
|
|
74
|
+
return `"${s.replace(/\\/g, '\\\\').replace(/"/g, '\\"')}"`;
|
|
75
|
+
}
|
|
76
|
+
function buildEdgeIndex(nodes, edges) {
|
|
77
|
+
const idToTitle = new Map();
|
|
78
|
+
for (const n of nodes)
|
|
79
|
+
idToTitle.set(n.id, n.title);
|
|
80
|
+
const result = new Map();
|
|
81
|
+
for (const n of nodes)
|
|
82
|
+
result.set(n.id, { outgoing: [], incoming: [] });
|
|
83
|
+
for (const e of edges) {
|
|
84
|
+
const fromTitle = idToTitle.get(e.from_node_id);
|
|
85
|
+
const toTitle = idToTitle.get(e.to_node_id);
|
|
86
|
+
if (!fromTitle || !toTitle)
|
|
87
|
+
continue;
|
|
88
|
+
const fromBucket = result.get(e.from_node_id);
|
|
89
|
+
const toBucket = result.get(e.to_node_id);
|
|
90
|
+
if (fromBucket)
|
|
91
|
+
fromBucket.outgoing.push({ to: toTitle, to_id: e.to_node_id, type: e.relation_type, label: e.label });
|
|
92
|
+
if (toBucket)
|
|
93
|
+
toBucket.incoming.push({ from: fromTitle, from_id: e.from_node_id, type: e.relation_type, label: e.label });
|
|
94
|
+
}
|
|
95
|
+
return result;
|
|
96
|
+
}
|
|
97
|
+
function renderFrontmatter(n, edges) {
|
|
98
|
+
const lines = ['---'];
|
|
99
|
+
lines.push(`id: ${n.id}`);
|
|
100
|
+
lines.push(`title: ${escapeYamlString(n.title)}`);
|
|
101
|
+
const tags = tagsArray(n.tags).filter(t => t !== WIKI_SCHEMA_TAG && t !== WIKI_INDEX_TAG);
|
|
102
|
+
if (tags.length > 0) {
|
|
103
|
+
lines.push(`tags: [${tags.map(escapeYamlString).join(', ')}]`);
|
|
104
|
+
}
|
|
105
|
+
if (isSchemaNode(n))
|
|
106
|
+
lines.push('schema: true');
|
|
107
|
+
if (isIndexNode(n))
|
|
108
|
+
lines.push('index: true');
|
|
109
|
+
if (n.pinned)
|
|
110
|
+
lines.push('pinned: true');
|
|
111
|
+
lines.push(`created_at: ${escapeYamlString(n.created_at)}`);
|
|
112
|
+
lines.push(`updated_at: ${escapeYamlString(n.updated_at)}`);
|
|
113
|
+
if (n.source_type)
|
|
114
|
+
lines.push(`source_type: ${escapeYamlString(n.source_type)}`);
|
|
115
|
+
if (n.source_id)
|
|
116
|
+
lines.push(`source_id: ${escapeYamlString(n.source_id)}`);
|
|
117
|
+
if (n.source_path)
|
|
118
|
+
lines.push(`source_path: ${escapeYamlString(n.source_path)}`);
|
|
119
|
+
if (edges.outgoing.length > 0 || edges.incoming.length > 0) {
|
|
120
|
+
lines.push('edges:');
|
|
121
|
+
if (edges.outgoing.length > 0) {
|
|
122
|
+
lines.push(' outgoing:');
|
|
123
|
+
for (const e of edges.outgoing) {
|
|
124
|
+
lines.push(` - to: ${escapeYamlString(e.to)}`);
|
|
125
|
+
lines.push(` to_id: ${e.to_id}`);
|
|
126
|
+
lines.push(` type: ${e.type}`);
|
|
127
|
+
if (e.label)
|
|
128
|
+
lines.push(` label: ${escapeYamlString(e.label)}`);
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
if (edges.incoming.length > 0) {
|
|
132
|
+
lines.push(' incoming:');
|
|
133
|
+
for (const e of edges.incoming) {
|
|
134
|
+
lines.push(` - from: ${escapeYamlString(e.from)}`);
|
|
135
|
+
lines.push(` from_id: ${e.from_id}`);
|
|
136
|
+
lines.push(` type: ${e.type}`);
|
|
137
|
+
if (e.label)
|
|
138
|
+
lines.push(` label: ${escapeYamlString(e.label)}`);
|
|
139
|
+
}
|
|
140
|
+
}
|
|
141
|
+
}
|
|
142
|
+
lines.push('---');
|
|
143
|
+
return lines.join('\n');
|
|
144
|
+
}
|
|
145
|
+
function renderNodeMarkdown(n, edges) {
|
|
146
|
+
const fm = renderFrontmatter(n, edges);
|
|
147
|
+
const body = n.body ?? '';
|
|
148
|
+
const heading = `# ${n.title}`;
|
|
149
|
+
return `${fm}\n\n${heading}\n\n${body}\n`;
|
|
150
|
+
}
|
|
151
|
+
/**
|
|
152
|
+
* Resolve a slug collision: if two nodes produce the same `<bucket>/<slug>.md`,
|
|
153
|
+
* append `-{shortId}` to the second's filename. We sort by created_at so the
|
|
154
|
+
* "older" node keeps the cleaner name.
|
|
155
|
+
*/
|
|
156
|
+
function assignFilenames(nodes) {
|
|
157
|
+
const bySlug = new Map();
|
|
158
|
+
for (const n of nodes) {
|
|
159
|
+
const key = `${bucketForNode(n)}/${filenameForNode(n)}`;
|
|
160
|
+
const list = bySlug.get(key);
|
|
161
|
+
if (list)
|
|
162
|
+
list.push(n);
|
|
163
|
+
else
|
|
164
|
+
bySlug.set(key, [n]);
|
|
165
|
+
}
|
|
166
|
+
const result = new Map();
|
|
167
|
+
for (const [, group] of bySlug) {
|
|
168
|
+
if (group.length === 1) {
|
|
169
|
+
const n = group[0];
|
|
170
|
+
result.set(n.id, { bucket: bucketForNode(n), filename: filenameForNode(n) });
|
|
171
|
+
continue;
|
|
172
|
+
}
|
|
173
|
+
// Stable sort: oldest first keeps clean name, others get suffixed.
|
|
174
|
+
const sorted = [...group].sort((a, b) => (a.created_at ?? '').localeCompare(b.created_at ?? '') || a.id.localeCompare(b.id));
|
|
175
|
+
sorted.forEach((n, i) => {
|
|
176
|
+
const bucket = bucketForNode(n);
|
|
177
|
+
const baseFile = filenameForNode(n);
|
|
178
|
+
if (i === 0) {
|
|
179
|
+
result.set(n.id, { bucket, filename: baseFile });
|
|
180
|
+
}
|
|
181
|
+
else {
|
|
182
|
+
const stem = baseFile.replace(/\.md$/, '');
|
|
183
|
+
const shortId = n.id.slice(0, 8);
|
|
184
|
+
result.set(n.id, { bucket, filename: `${stem}-${shortId}.md` });
|
|
185
|
+
}
|
|
186
|
+
});
|
|
187
|
+
}
|
|
188
|
+
return result;
|
|
189
|
+
}
|
|
190
|
+
function walkMarkdownFiles(dir) {
|
|
191
|
+
const out = [];
|
|
192
|
+
const stack = [dir];
|
|
193
|
+
while (stack.length > 0) {
|
|
194
|
+
const cur = stack.pop();
|
|
195
|
+
let entries;
|
|
196
|
+
try {
|
|
197
|
+
entries = fs.readdirSync(cur, { withFileTypes: true });
|
|
198
|
+
}
|
|
199
|
+
catch {
|
|
200
|
+
continue;
|
|
201
|
+
}
|
|
202
|
+
for (const entry of entries) {
|
|
203
|
+
const full = path.join(cur, entry.name);
|
|
204
|
+
if (entry.isDirectory())
|
|
205
|
+
stack.push(full);
|
|
206
|
+
else if (entry.isFile() && entry.name.endsWith('.md'))
|
|
207
|
+
out.push(full);
|
|
208
|
+
}
|
|
209
|
+
}
|
|
210
|
+
return out;
|
|
211
|
+
}
|
|
212
|
+
function writeReadme(baseDir) {
|
|
213
|
+
const readmePath = path.join(baseDir, 'README.md');
|
|
214
|
+
if (fs.existsSync(readmePath))
|
|
215
|
+
return;
|
|
216
|
+
const content = `# Project Wiki (auto-generated)
|
|
217
|
+
|
|
218
|
+
This directory is a one-way Markdown mirror of the wiki nodes stored in
|
|
219
|
+
CLITrigger's database. The application regenerates these files whenever
|
|
220
|
+
wiki content changes — **edits made directly to files here are
|
|
221
|
+
overwritten on the next sync.**
|
|
222
|
+
|
|
223
|
+
To track this directory in git, ensure your \`.gitignore\` ignores only
|
|
224
|
+
\`.clitrigger/raw/\` (the raw source snapshots) rather than the entire
|
|
225
|
+
\`.clitrigger/\` directory.
|
|
226
|
+
|
|
227
|
+
Layout:
|
|
228
|
+
- \`<entity-type>/<slug>.md\` — one file per wiki node, grouped by first tag
|
|
229
|
+
- \`_untagged/\` — nodes with no tags
|
|
230
|
+
- \`_schema.md\` — the wiki schema (entity types + ingest conventions)
|
|
231
|
+
`;
|
|
232
|
+
try {
|
|
233
|
+
fs.writeFileSync(readmePath, content, 'utf-8');
|
|
234
|
+
}
|
|
235
|
+
catch { /* non-fatal */ }
|
|
236
|
+
}
|
|
237
|
+
export function exportProjectWikiSync(projectId) {
|
|
238
|
+
const project = queries.getProjectById(projectId);
|
|
239
|
+
if (!project || !project.path)
|
|
240
|
+
return null;
|
|
241
|
+
if (!fs.existsSync(project.path))
|
|
242
|
+
return null;
|
|
243
|
+
const baseDir = path.join(project.path, WIKI_DIR_NAME, WIKI_SUBDIR);
|
|
244
|
+
fs.mkdirSync(baseDir, { recursive: true });
|
|
245
|
+
writeReadme(baseDir);
|
|
246
|
+
// Refresh the auto-maintained index node before reading the snapshot so the
|
|
247
|
+
// exported _index.md and the in-DB index stay in sync.
|
|
248
|
+
try {
|
|
249
|
+
regenerateIndexNode(projectId);
|
|
250
|
+
}
|
|
251
|
+
catch (err) {
|
|
252
|
+
console.warn('[wiki-exporter] index regeneration failed:', err instanceof Error ? err.message : err);
|
|
253
|
+
}
|
|
254
|
+
const nodes = queries.getMemoryNodesByProjectId(projectId);
|
|
255
|
+
const edges = queries.getMemoryEdgesByProjectId(projectId);
|
|
256
|
+
const edgeIndex = buildEdgeIndex(nodes, edges);
|
|
257
|
+
const filenameMap = assignFilenames(nodes);
|
|
258
|
+
const expected = new Set();
|
|
259
|
+
let written = 0;
|
|
260
|
+
for (const n of nodes) {
|
|
261
|
+
const placement = filenameMap.get(n.id);
|
|
262
|
+
if (!placement)
|
|
263
|
+
continue;
|
|
264
|
+
const subDir = placement.bucket ? path.join(baseDir, placement.bucket) : baseDir;
|
|
265
|
+
fs.mkdirSync(subDir, { recursive: true });
|
|
266
|
+
const filePath = path.join(subDir, placement.filename);
|
|
267
|
+
// Path traversal guard
|
|
268
|
+
const resolved = path.resolve(filePath);
|
|
269
|
+
const resolvedBase = path.resolve(baseDir);
|
|
270
|
+
if (!resolved.startsWith(resolvedBase + path.sep))
|
|
271
|
+
continue;
|
|
272
|
+
const summary = edgeIndex.get(n.id) ?? { outgoing: [], incoming: [] };
|
|
273
|
+
const content = renderNodeMarkdown(n, summary);
|
|
274
|
+
try {
|
|
275
|
+
const existing = fs.existsSync(filePath) ? fs.readFileSync(filePath, 'utf-8') : null;
|
|
276
|
+
if (existing !== content) {
|
|
277
|
+
fs.writeFileSync(filePath, content, 'utf-8');
|
|
278
|
+
}
|
|
279
|
+
expected.add(resolved);
|
|
280
|
+
written++;
|
|
281
|
+
}
|
|
282
|
+
catch (err) {
|
|
283
|
+
console.warn('[wiki-exporter] write failed:', err);
|
|
284
|
+
}
|
|
285
|
+
}
|
|
286
|
+
// Cleanup orphaned files (deleted nodes, renamed slugs, etc.)
|
|
287
|
+
let removed = 0;
|
|
288
|
+
const existingFiles = walkMarkdownFiles(baseDir);
|
|
289
|
+
for (const file of existingFiles) {
|
|
290
|
+
const resolved = path.resolve(file);
|
|
291
|
+
if (path.basename(resolved) === 'README.md')
|
|
292
|
+
continue;
|
|
293
|
+
if (!expected.has(resolved)) {
|
|
294
|
+
try {
|
|
295
|
+
fs.unlinkSync(resolved);
|
|
296
|
+
removed++;
|
|
297
|
+
}
|
|
298
|
+
catch { /* ignore */ }
|
|
299
|
+
}
|
|
300
|
+
}
|
|
301
|
+
// Cleanup empty bucket directories
|
|
302
|
+
let removedDirs = 0;
|
|
303
|
+
let entries;
|
|
304
|
+
try {
|
|
305
|
+
entries = fs.readdirSync(baseDir, { withFileTypes: true });
|
|
306
|
+
}
|
|
307
|
+
catch {
|
|
308
|
+
entries = [];
|
|
309
|
+
}
|
|
310
|
+
for (const entry of entries) {
|
|
311
|
+
if (!entry.isDirectory())
|
|
312
|
+
continue;
|
|
313
|
+
const dirPath = path.join(baseDir, entry.name);
|
|
314
|
+
try {
|
|
315
|
+
const inner = fs.readdirSync(dirPath);
|
|
316
|
+
if (inner.length === 0) {
|
|
317
|
+
fs.rmdirSync(dirPath);
|
|
318
|
+
removedDirs++;
|
|
319
|
+
}
|
|
320
|
+
}
|
|
321
|
+
catch { /* ignore */ }
|
|
322
|
+
}
|
|
323
|
+
return { baseDir, written, removed, removedDirs };
|
|
324
|
+
}
|
|
325
|
+
/**
|
|
326
|
+
* Read-only comparison of `<project>/.clitrigger/wiki/` files against what
|
|
327
|
+
* `exportProjectWikiSync` would currently emit. Used by the "Check for disk
|
|
328
|
+
* changes" UI so users can spot edits made in Obsidian (or anything else)
|
|
329
|
+
* without committing to a bidirectional sync that risks losing in-flight
|
|
330
|
+
* work. Caller decides what to do — apply, ignore, or re-export to overwrite.
|
|
331
|
+
*/
|
|
332
|
+
export function diffProjectWikiSync(projectId) {
|
|
333
|
+
const project = queries.getProjectById(projectId);
|
|
334
|
+
if (!project || !project.path)
|
|
335
|
+
return null;
|
|
336
|
+
const baseDir = path.join(project.path, WIKI_DIR_NAME, WIKI_SUBDIR);
|
|
337
|
+
if (!fs.existsSync(baseDir))
|
|
338
|
+
return [];
|
|
339
|
+
// Refresh the index so it doesn't show as "modified" just because we haven't
|
|
340
|
+
// exported recently. This is read-only as far as the disk is concerned.
|
|
341
|
+
try {
|
|
342
|
+
regenerateIndexNode(projectId);
|
|
343
|
+
}
|
|
344
|
+
catch { /* ignore */ }
|
|
345
|
+
const nodes = queries.getMemoryNodesByProjectId(projectId);
|
|
346
|
+
const edges = queries.getMemoryEdgesByProjectId(projectId);
|
|
347
|
+
const edgeIndex = buildEdgeIndex(nodes, edges);
|
|
348
|
+
const filenameMap = assignFilenames(nodes);
|
|
349
|
+
const expectedByAbs = new Map();
|
|
350
|
+
for (const n of nodes) {
|
|
351
|
+
const placement = filenameMap.get(n.id);
|
|
352
|
+
if (!placement)
|
|
353
|
+
continue;
|
|
354
|
+
const subDir = placement.bucket ? path.join(baseDir, placement.bucket) : baseDir;
|
|
355
|
+
const filePath = path.join(subDir, placement.filename);
|
|
356
|
+
const absPath = path.resolve(filePath);
|
|
357
|
+
const summary = edgeIndex.get(n.id) ?? { outgoing: [], incoming: [] };
|
|
358
|
+
expectedByAbs.set(absPath, {
|
|
359
|
+
node: n,
|
|
360
|
+
content: renderNodeMarkdown(n, summary),
|
|
361
|
+
relativeKey: placement.bucket ? `${placement.bucket}/${placement.filename}` : placement.filename,
|
|
362
|
+
absPath,
|
|
363
|
+
});
|
|
364
|
+
}
|
|
365
|
+
const diffs = [];
|
|
366
|
+
const seenOnDisk = new Set();
|
|
367
|
+
for (const file of walkMarkdownFiles(baseDir)) {
|
|
368
|
+
if (path.basename(file) === 'README.md')
|
|
369
|
+
continue;
|
|
370
|
+
const abs = path.resolve(file);
|
|
371
|
+
seenOnDisk.add(abs);
|
|
372
|
+
const exp = expectedByAbs.get(abs);
|
|
373
|
+
const relativeKey = path.relative(baseDir, file).split(path.sep).join('/');
|
|
374
|
+
if (!exp) {
|
|
375
|
+
let bytes = 0;
|
|
376
|
+
try {
|
|
377
|
+
bytes = fs.statSync(file).size;
|
|
378
|
+
}
|
|
379
|
+
catch { /* ignore */ }
|
|
380
|
+
diffs.push({ type: 'untracked', filename: relativeKey, diskBytes: bytes });
|
|
381
|
+
continue;
|
|
382
|
+
}
|
|
383
|
+
let onDisk;
|
|
384
|
+
try {
|
|
385
|
+
onDisk = fs.readFileSync(file, 'utf-8');
|
|
386
|
+
}
|
|
387
|
+
catch {
|
|
388
|
+
continue;
|
|
389
|
+
}
|
|
390
|
+
if (onDisk !== exp.content) {
|
|
391
|
+
diffs.push({
|
|
392
|
+
type: 'modified',
|
|
393
|
+
filename: exp.relativeKey,
|
|
394
|
+
id: exp.node.id,
|
|
395
|
+
title: exp.node.title,
|
|
396
|
+
diskBytes: onDisk.length,
|
|
397
|
+
dbBytes: exp.content.length,
|
|
398
|
+
});
|
|
399
|
+
}
|
|
400
|
+
}
|
|
401
|
+
for (const [abs, exp] of expectedByAbs) {
|
|
402
|
+
if (!seenOnDisk.has(abs)) {
|
|
403
|
+
diffs.push({
|
|
404
|
+
type: 'missing',
|
|
405
|
+
filename: exp.relativeKey,
|
|
406
|
+
id: exp.node.id,
|
|
407
|
+
title: exp.node.title,
|
|
408
|
+
dbBytes: exp.content.length,
|
|
409
|
+
});
|
|
410
|
+
}
|
|
411
|
+
}
|
|
412
|
+
return diffs;
|
|
413
|
+
}
|
|
414
|
+
/**
|
|
415
|
+
* Best-effort wiki export. Errors are swallowed so callers can fire-and-forget
|
|
416
|
+
* after any wiki mutation without worrying about blocking the response or
|
|
417
|
+
* breaking the request on FS issues.
|
|
418
|
+
*/
|
|
419
|
+
export function dispatchWikiExport(projectId) {
|
|
420
|
+
// Defer to next tick so we don't add latency to the triggering request.
|
|
421
|
+
setImmediate(() => {
|
|
422
|
+
try {
|
|
423
|
+
exportProjectWikiSync(projectId);
|
|
424
|
+
}
|
|
425
|
+
catch (err) {
|
|
426
|
+
console.warn('[wiki-exporter] dispatch failed:', err instanceof Error ? err.message : err);
|
|
427
|
+
}
|
|
428
|
+
});
|
|
429
|
+
}
|
|
430
|
+
//# sourceMappingURL=wiki-exporter.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"wiki-exporter.js","sourceRoot":"","sources":["../../../src/server/services/wiki-exporter.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import type { MemoryNode } from '../db/queries.js';
|
|
2
|
+
export declare const WIKI_INDEX_TAG = "__wiki_index__";
|
|
3
|
+
export declare function isWikiIndexNode(n: MemoryNode): boolean;
|
|
4
|
+
/**
|
|
5
|
+
* Upsert the project's auto-maintained index node (`__wiki_index__` tag).
|
|
6
|
+
* Body is a Markdown catalog grouped by first tag, with one-line summaries.
|
|
7
|
+
* Skipped on body equality so wiki-exporter's idempotent writes stay quiet.
|
|
8
|
+
*/
|
|
9
|
+
export declare function regenerateIndexNode(projectId: string): MemoryNode | null;
|
|
10
|
+
//# sourceMappingURL=wiki-index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"wiki-index.d.ts","sourceRoot":"","sources":["../../../src/server/services/wiki-index.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAEnD,eAAO,MAAM,cAAc,mBAAmB,CAAC;AAc/C,wBAAgB,eAAe,CAAC,CAAC,EAAE,UAAU,GAAG,OAAO,CAEtD;AAgED;;;;GAIG;AACH,wBAAgB,mBAAmB,CAAC,SAAS,EAAE,MAAM,GAAG,UAAU,GAAG,IAAI,CA0BxE"}
|
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
import * as queries from '../db/queries.js';
|
|
2
|
+
export const WIKI_INDEX_TAG = '__wiki_index__';
|
|
3
|
+
const WIKI_SCHEMA_TAG = '__wiki_schema__';
|
|
4
|
+
const INDEX_TITLE = 'Wiki Index';
|
|
5
|
+
const SUMMARY_MAX_CHARS = 80;
|
|
6
|
+
const UNTAGGED_BUCKET = '_Untagged';
|
|
7
|
+
function tagsArray(raw) {
|
|
8
|
+
if (!raw)
|
|
9
|
+
return [];
|
|
10
|
+
try {
|
|
11
|
+
const parsed = JSON.parse(raw);
|
|
12
|
+
return Array.isArray(parsed) ? parsed.map(String).map(s => s.trim()).filter(Boolean) : [];
|
|
13
|
+
}
|
|
14
|
+
catch {
|
|
15
|
+
return [];
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
export function isWikiIndexNode(n) {
|
|
19
|
+
return tagsArray(n.tags).includes(WIKI_INDEX_TAG);
|
|
20
|
+
}
|
|
21
|
+
function isWikiSchemaNode(n) {
|
|
22
|
+
return tagsArray(n.tags).includes(WIKI_SCHEMA_TAG);
|
|
23
|
+
}
|
|
24
|
+
function isSystemNode(n) {
|
|
25
|
+
return isWikiIndexNode(n) || isWikiSchemaNode(n);
|
|
26
|
+
}
|
|
27
|
+
function firstSentence(body) {
|
|
28
|
+
const flat = body.replace(/\s+/g, ' ').trim();
|
|
29
|
+
if (!flat)
|
|
30
|
+
return '';
|
|
31
|
+
const cut = flat.slice(0, SUMMARY_MAX_CHARS);
|
|
32
|
+
return cut.length < flat.length ? `${cut}…` : cut;
|
|
33
|
+
}
|
|
34
|
+
function getExistingIndexNode(projectId) {
|
|
35
|
+
const all = queries.getMemoryNodesByProjectId(projectId);
|
|
36
|
+
return all.find(isWikiIndexNode);
|
|
37
|
+
}
|
|
38
|
+
function buildIndexBody(allNodes) {
|
|
39
|
+
const visible = allNodes.filter(n => !isSystemNode(n));
|
|
40
|
+
const grouped = new Map();
|
|
41
|
+
for (const n of visible) {
|
|
42
|
+
const tags = tagsArray(n.tags).filter(t => t !== WIKI_INDEX_TAG && t !== WIKI_SCHEMA_TAG);
|
|
43
|
+
const key = tags[0] ?? UNTAGGED_BUCKET;
|
|
44
|
+
if (!grouped.has(key))
|
|
45
|
+
grouped.set(key, []);
|
|
46
|
+
grouped.get(key).push(n);
|
|
47
|
+
}
|
|
48
|
+
const lines = [];
|
|
49
|
+
lines.push('# Wiki Index');
|
|
50
|
+
lines.push('');
|
|
51
|
+
lines.push(`_Auto-maintained. ${visible.length} entr${visible.length === 1 ? 'y' : 'ies'} across ${grouped.size} tag${grouped.size === 1 ? '' : 's'}. Last sync: ${new Date().toISOString()}._`);
|
|
52
|
+
lines.push('_Edits to this entry are overwritten on the next wiki change._');
|
|
53
|
+
lines.push('');
|
|
54
|
+
if (visible.length === 0) {
|
|
55
|
+
lines.push('No wiki entries yet — run Ingest to create some.');
|
|
56
|
+
return lines.join('\n') + '\n';
|
|
57
|
+
}
|
|
58
|
+
const sortedGroups = [...grouped.entries()].sort(([a], [b]) => {
|
|
59
|
+
if (a === UNTAGGED_BUCKET)
|
|
60
|
+
return 1;
|
|
61
|
+
if (b === UNTAGGED_BUCKET)
|
|
62
|
+
return -1;
|
|
63
|
+
return a.localeCompare(b);
|
|
64
|
+
});
|
|
65
|
+
for (const [tag, group] of sortedGroups) {
|
|
66
|
+
const sortedGroup = [...group].sort((a, b) => a.title.localeCompare(b.title));
|
|
67
|
+
lines.push(`## ${tag} (${sortedGroup.length})`);
|
|
68
|
+
for (const n of sortedGroup) {
|
|
69
|
+
const summary = firstSentence(n.body || '');
|
|
70
|
+
lines.push(`- [[${n.title}]]${summary ? ` — ${summary}` : ''}`);
|
|
71
|
+
}
|
|
72
|
+
lines.push('');
|
|
73
|
+
}
|
|
74
|
+
return lines.join('\n').trimEnd() + '\n';
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Upsert the project's auto-maintained index node (`__wiki_index__` tag).
|
|
78
|
+
* Body is a Markdown catalog grouped by first tag, with one-line summaries.
|
|
79
|
+
* Skipped on body equality so wiki-exporter's idempotent writes stay quiet.
|
|
80
|
+
*/
|
|
81
|
+
export function regenerateIndexNode(projectId) {
|
|
82
|
+
const project = queries.getProjectById(projectId);
|
|
83
|
+
if (!project)
|
|
84
|
+
return null;
|
|
85
|
+
const allNodes = queries.getMemoryNodesByProjectId(projectId);
|
|
86
|
+
const visibleCount = allNodes.filter(n => !isSystemNode(n)).length;
|
|
87
|
+
const existing = getExistingIndexNode(projectId);
|
|
88
|
+
// Skip creation when there's nothing to index AND no existing index — avoids
|
|
89
|
+
// creating an empty system node on a fresh project that hasn't ingested yet.
|
|
90
|
+
if (!existing && visibleCount === 0)
|
|
91
|
+
return null;
|
|
92
|
+
const newBody = buildIndexBody(allNodes);
|
|
93
|
+
if (existing) {
|
|
94
|
+
if (existing.body === newBody)
|
|
95
|
+
return existing;
|
|
96
|
+
return queries.updateMemoryNode(existing.id, { body: newBody }) ?? existing;
|
|
97
|
+
}
|
|
98
|
+
return queries.createMemoryNode(projectId, INDEX_TITLE, newBody, JSON.stringify([WIKI_INDEX_TAG]), 1);
|
|
99
|
+
}
|
|
100
|
+
//# sourceMappingURL=wiki-index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"wiki-index.js","sourceRoot":"","sources":["../../../src/server/services/wiki-index.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/server/websocket/index.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,MAAM,CAAC;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/server/websocket/index.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,MAAM,CAAC;AAQnC,wBAAgB,aAAa,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CA+JlD"}
|
|
@@ -2,6 +2,7 @@ import { WebSocketServer } from 'ws';
|
|
|
2
2
|
import { broadcaster, encodeSessionFrame } from './broadcaster.js';
|
|
3
3
|
import { sessionMiddleware } from '../middleware/auth.js';
|
|
4
4
|
import { claudeManager } from '../services/claude-manager.js';
|
|
5
|
+
import { sessionManager } from '../services/session-manager.js';
|
|
5
6
|
import { getTodoById, createTaskLog, getSessionById, createSessionLog, getSessionRawChunks } from '../db/queries.js';
|
|
6
7
|
export function initWebSocket(server) {
|
|
7
8
|
const wss = new WebSocketServer({ noServer: true });
|
|
@@ -98,22 +99,22 @@ export function initWebSocket(server) {
|
|
|
98
99
|
}
|
|
99
100
|
// ── xterm.js terminal channel (Sessions tab) ──
|
|
100
101
|
// Subscribe a client to the high-frequency binary output for a session.
|
|
101
|
-
// On subscribe we
|
|
102
|
-
//
|
|
102
|
+
// On subscribe we drain any in-flight pending bytes to DB (so the
|
|
103
|
+
// persisted chunks are the single source of truth), then replay
|
|
104
|
+
// them and send `session:replay-end`. Subscribing before the flush
|
|
105
|
+
// is intentional: any chunk delivered after this synchronous handler
|
|
106
|
+
// returns will be live-broadcast, and JS single-threading guarantees
|
|
107
|
+
// no PTY data event interleaves between subscribe and the DB read.
|
|
103
108
|
if (msg.type === 'session:subscribe' && typeof msg.sessionId === 'string') {
|
|
104
109
|
const session = getSessionById(msg.sessionId);
|
|
105
110
|
if (session) {
|
|
106
111
|
broadcaster.subscribe(ws, msg.sessionId);
|
|
107
112
|
try {
|
|
113
|
+
sessionManager.flushPendingRaw(msg.sessionId);
|
|
108
114
|
const chunks = getSessionRawChunks(msg.sessionId);
|
|
109
115
|
for (const c of chunks) {
|
|
110
116
|
ws.send(encodeSessionFrame(msg.sessionId, c.bytes), { binary: true });
|
|
111
117
|
}
|
|
112
|
-
if (session.process_pid) {
|
|
113
|
-
const tail = claudeManager.getRawHistory(session.process_pid);
|
|
114
|
-
if (tail)
|
|
115
|
-
ws.send(encodeSessionFrame(msg.sessionId, tail), { binary: true });
|
|
116
|
-
}
|
|
117
118
|
}
|
|
118
119
|
catch { /* ignore replay errors */ }
|
|
119
120
|
ws.send(JSON.stringify({ type: 'session:replay-end', sessionId: msg.sessionId }));
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/server/websocket/index.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/server/websocket/index.ts"],"names":[],"mappings":"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"}
|