@inharness-ai/claude4spec 1.0.13 → 1.0.15
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 +18 -0
- package/dist/bin/c4s/commands/find-references.d.ts +13 -0
- package/dist/bin/c4s/commands/find-references.js +81 -0
- package/dist/bin/c4s/commands/find-references.js.map +1 -0
- package/dist/bin/c4s.js +6 -0
- package/dist/bin/c4s.js.map +1 -1
- package/dist/client/assets/{arc-E0e7X_zn.js → arc-Bm0IE9-2.js} +1 -1
- package/dist/client/assets/{architectureDiagram-3BPJPVTR-BzlqOVZv.js → architectureDiagram-3BPJPVTR-GJ4QxX0Q.js} +1 -1
- package/dist/client/assets/{blockDiagram-GPEHLZMM-BIQcApN7.js → blockDiagram-GPEHLZMM-C9rZbfxq.js} +1 -1
- package/dist/client/assets/{c4Diagram-AAUBKEIU-CDU0V1yk.js → c4Diagram-AAUBKEIU-DyVuHGeV.js} +1 -1
- package/dist/client/assets/channel-BGn39mc8.js +1 -0
- package/dist/client/assets/{chunk-2J33WTMH-PtDSwC5f.js → chunk-2J33WTMH-DePzEFC8.js} +1 -1
- package/dist/client/assets/{chunk-4BX2VUAB-DTUPWrSO.js → chunk-4BX2VUAB-NZkVFx6P.js} +1 -1
- package/dist/client/assets/{chunk-55IACEB6-Cpd59xZT.js → chunk-55IACEB6-DSelTsfa.js} +1 -1
- package/dist/client/assets/{chunk-727SXJPM-C4DOvpJT.js → chunk-727SXJPM-Vk_bMeuW.js} +1 -1
- package/dist/client/assets/{chunk-AQP2D5EJ-CtjeHPBB.js → chunk-AQP2D5EJ-Bv_5j6lW.js} +1 -1
- package/dist/client/assets/{chunk-FMBD7UC4-CZA3OvVr.js → chunk-FMBD7UC4-CIwy6WRQ.js} +1 -1
- package/dist/client/assets/{chunk-ND2GUHAM-Cbx6nQHm.js → chunk-ND2GUHAM-C-7ZR2Kw.js} +1 -1
- package/dist/client/assets/{chunk-QZHKN3VN-3DunELI_.js → chunk-QZHKN3VN-D2pOGWp9.js} +1 -1
- package/dist/client/assets/classDiagram-4FO5ZUOK-DZ5eaGnY.js +1 -0
- package/dist/client/assets/classDiagram-v2-Q7XG4LA2-DZ5eaGnY.js +1 -0
- package/dist/client/assets/{cose-bilkent-S5V4N54A-CKYJnuL7.js → cose-bilkent-S5V4N54A-NgRxSzcd.js} +1 -1
- package/dist/client/assets/{dagre-BM42HDAG-BrvRwrr_.js → dagre-BM42HDAG-kwaDBrFq.js} +1 -1
- package/dist/client/assets/{diagram-2AECGRRQ-BaVLuzcD.js → diagram-2AECGRRQ-B5OMokEe.js} +1 -1
- package/dist/client/assets/{diagram-5GNKFQAL-9Cu7Wa7J.js → diagram-5GNKFQAL-9h9Lsrr_.js} +1 -1
- package/dist/client/assets/{diagram-KO2AKTUF-XKiCVdjO.js → diagram-KO2AKTUF-DcNC4jPN.js} +1 -1
- package/dist/client/assets/{diagram-LMA3HP47-DerecU5v.js → diagram-LMA3HP47-D41zybvJ.js} +1 -1
- package/dist/client/assets/{diagram-OG6HWLK6-BWcREvZ9.js → diagram-OG6HWLK6-D12dQiCG.js} +1 -1
- package/dist/client/assets/{erDiagram-TEJ5UH35-DU3BBQJY.js → erDiagram-TEJ5UH35-brqTv2OJ.js} +1 -1
- package/dist/client/assets/{flowDiagram-I6XJVG4X-DXO_IJeR.js → flowDiagram-I6XJVG4X-D6q2xyWg.js} +1 -1
- package/dist/client/assets/{ganttDiagram-6RSMTGT7-CXiFZEPx.js → ganttDiagram-6RSMTGT7-DlH9o0CJ.js} +1 -1
- package/dist/client/assets/{gitGraphDiagram-PVQCEYII-DHewdln-.js → gitGraphDiagram-PVQCEYII-CgNLFhAT.js} +1 -1
- package/dist/client/assets/{index-DT5g2AtL.js → index-C-gTQA-n.js} +1 -1
- package/dist/client/assets/{index-DD0GkjkG.js → index-DDRzJojo.js} +1 -1
- package/dist/client/assets/{index-BTXWIk4x.css → index-DirDnayu.css} +1 -1
- package/dist/client/assets/{index-DcIG_8JB.js → index-qO9stCkx.js} +189 -179
- package/dist/client/assets/{infoDiagram-5YYISTIA-CN40PAGW.js → infoDiagram-5YYISTIA-ThuQNCvi.js} +1 -1
- package/dist/client/assets/{ishikawaDiagram-YF4QCWOH-B8KsyuPk.js → ishikawaDiagram-YF4QCWOH-m-2DHbkK.js} +1 -1
- package/dist/client/assets/{journeyDiagram-JHISSGLW-BlEb3E_P.js → journeyDiagram-JHISSGLW-CNCSJPeY.js} +1 -1
- package/dist/client/assets/{kanban-definition-UN3LZRKU-B080CGS9.js → kanban-definition-UN3LZRKU-CtzjrW3p.js} +1 -1
- package/dist/client/assets/{linear-D6Tg-IET.js → linear-BF1Qhpjc.js} +1 -1
- package/dist/client/assets/{mermaid.core-DP18nW3T.js → mermaid.core-fKaK1Sz_.js} +4 -4
- package/dist/client/assets/{mindmap-definition-RKZ34NQL-bfo7Qm5I.js → mindmap-definition-RKZ34NQL-CXuVRuzz.js} +1 -1
- package/dist/client/assets/{pieDiagram-4H26LBE5-ZsPztPu6.js → pieDiagram-4H26LBE5-DdL9uKdO.js} +1 -1
- package/dist/client/assets/{quadrantDiagram-W4KKPZXB-DKrTleIL.js → quadrantDiagram-W4KKPZXB-C_0FG9xH.js} +1 -1
- package/dist/client/assets/{requirementDiagram-4Y6WPE33-D4YX8ZgG.js → requirementDiagram-4Y6WPE33-Qmg8C7k6.js} +1 -1
- package/dist/client/assets/{sankeyDiagram-5OEKKPKP-Bo-xm6Mc.js → sankeyDiagram-5OEKKPKP-DuIvgSjA.js} +1 -1
- package/dist/client/assets/{sequenceDiagram-3UESZ5HK-CozgdKp6.js → sequenceDiagram-3UESZ5HK-B4JsFW9i.js} +1 -1
- package/dist/client/assets/{stateDiagram-AJRCARHV-CiK61MwV.js → stateDiagram-AJRCARHV-lTFw6Md4.js} +1 -1
- package/dist/client/assets/stateDiagram-v2-BHNVJYJU-D2iiMzxh.js +1 -0
- package/dist/client/assets/{timeline-definition-PNZ67QCA-CgHoguI7.js → timeline-definition-PNZ67QCA-C7Hc5KbB.js} +1 -1
- package/dist/client/assets/{vennDiagram-CIIHVFJN-TY32dxQb.js → vennDiagram-CIIHVFJN-DMyGzBh7.js} +1 -1
- package/dist/client/assets/{wardley-L42UT6IY-C6Q7VFwH.js → wardley-L42UT6IY-BjA5T0YY.js} +1 -1
- package/dist/client/assets/{wardleyDiagram-YWT4CUSO-nZLnVsQL.js → wardleyDiagram-YWT4CUSO-BhOipIZG.js} +1 -1
- package/dist/client/assets/{xychartDiagram-2RQKCTM6-DHdYRHEr.js → xychartDiagram-2RQKCTM6-Czx4--PM.js} +1 -1
- package/dist/client/index.html +2 -2
- package/dist/core/references/find-references.d.ts +13 -0
- package/dist/core/references/find-references.js +41 -0
- package/dist/core/references/find-references.js.map +1 -0
- package/dist/core/references/index.d.ts +2 -0
- package/dist/core/references/index.js +2 -0
- package/dist/core/references/index.js.map +1 -0
- package/dist/core/references/types.d.ts +45 -0
- package/dist/core/references/types.js +9 -0
- package/dist/core/references/types.js.map +1 -0
- package/dist/server/config.d.ts +9 -0
- package/dist/server/config.js +6 -0
- package/dist/server/config.js.map +1 -1
- package/dist/server/core/plugin-host/entities-router.d.ts +2 -1
- package/dist/server/core/plugin-host/entities-router.js +19 -13
- package/dist/server/core/plugin-host/entities-router.js.map +1 -1
- package/dist/server/core/plugin-host/host.js +4 -9
- package/dist/server/core/plugin-host/host.js.map +1 -1
- package/dist/server/core/plugin-host/types.d.ts +9 -14
- package/dist/server/db/migrations/035_m29_slug_identity.sql +248 -0
- package/dist/server/domain/raw-entity-reader.d.ts +3 -5
- package/dist/server/domain/raw-entity-reader.js +28 -39
- package/dist/server/domain/raw-entity-reader.js.map +1 -1
- package/dist/server/entities/ac/ac-analysis.service.d.ts +54 -0
- package/dist/server/entities/ac/ac-analysis.service.js +162 -0
- package/dist/server/entities/ac/ac-analysis.service.js.map +1 -0
- package/dist/server/entities/ac/mcp-server.d.ts +8 -0
- package/dist/server/entities/ac/mcp-server.js +30 -2
- package/dist/server/entities/ac/mcp-server.js.map +1 -1
- package/dist/server/entities/ac/plugin.js +4 -2
- package/dist/server/entities/ac/plugin.js.map +1 -1
- package/dist/server/entities/ac/serializer.js +1 -1
- package/dist/server/entities/ac/serializer.js.map +1 -1
- package/dist/server/entities/ac/services.d.ts +19 -7
- package/dist/server/entities/ac/services.js +65 -42
- package/dist/server/entities/ac/services.js.map +1 -1
- package/dist/server/entities/database-table/plugin.js +1 -2
- package/dist/server/entities/database-table/plugin.js.map +1 -1
- package/dist/server/entities/database-table/serializer.js +1 -1
- package/dist/server/entities/database-table/serializer.js.map +1 -1
- package/dist/server/entities/database-table/services.d.ts +19 -7
- package/dist/server/entities/database-table/services.js +74 -47
- package/dist/server/entities/database-table/services.js.map +1 -1
- package/dist/server/entities/dto/plugin.js +1 -2
- package/dist/server/entities/dto/plugin.js.map +1 -1
- package/dist/server/entities/dto/serializer.js +2 -2
- package/dist/server/entities/dto/serializer.js.map +1 -1
- package/dist/server/entities/dto/services.d.ts +19 -7
- package/dist/server/entities/dto/services.js +70 -47
- package/dist/server/entities/dto/services.js.map +1 -1
- package/dist/server/entities/endpoint/plugin.js +1 -2
- package/dist/server/entities/endpoint/plugin.js.map +1 -1
- package/dist/server/entities/endpoint/serializer.js +4 -4
- package/dist/server/entities/endpoint/serializer.js.map +1 -1
- package/dist/server/entities/endpoint/services.d.ts +21 -9
- package/dist/server/entities/endpoint/services.js +91 -63
- package/dist/server/entities/endpoint/services.js.map +1 -1
- package/dist/server/entities/mutate-opts.d.ts +15 -0
- package/dist/server/entities/mutate-opts.js +2 -0
- package/dist/server/entities/mutate-opts.js.map +1 -0
- package/dist/server/entities/ui-view/plugin.js +1 -2
- package/dist/server/entities/ui-view/plugin.js.map +1 -1
- package/dist/server/entities/ui-view/serializer.js +1 -1
- package/dist/server/entities/ui-view/serializer.js.map +1 -1
- package/dist/server/entities/ui-view/services.d.ts +19 -7
- package/dist/server/entities/ui-view/services.js +65 -42
- package/dist/server/entities/ui-view/services.js.map +1 -1
- package/dist/server/fs/entities-watcher.d.ts +31 -0
- package/dist/server/fs/entities-watcher.js +68 -0
- package/dist/server/fs/entities-watcher.js.map +1 -0
- package/dist/server/fs/watcher.js +7 -1
- package/dist/server/fs/watcher.js.map +1 -1
- package/dist/server/index.js +112 -6
- package/dist/server/index.js.map +1 -1
- package/dist/server/mcp/reference-tools.d.ts +3 -0
- package/dist/server/mcp/reference-tools.js +25 -161
- package/dist/server/mcp/reference-tools.js.map +1 -1
- package/dist/server/routes/static.d.ts +11 -0
- package/dist/server/routes/static.js +44 -0
- package/dist/server/routes/static.js.map +1 -0
- package/dist/server/services/entity-indexer.d.ts +42 -0
- package/dist/server/services/entity-indexer.js +179 -0
- package/dist/server/services/entity-indexer.js.map +1 -0
- package/dist/server/services/entity-store.d.ts +68 -0
- package/dist/server/services/entity-store.js +162 -0
- package/dist/server/services/entity-store.js.map +1 -0
- package/dist/server/services/entity-writer.d.ts +12 -1
- package/dist/server/services/entity-writer.js +22 -11
- package/dist/server/services/entity-writer.js.map +1 -1
- package/dist/server/services/git.js +6 -1
- package/dist/server/services/git.js.map +1 -1
- package/dist/server/services/pages.js +5 -1
- package/dist/server/services/pages.js.map +1 -1
- package/dist/server/services/references.d.ts +25 -0
- package/dist/server/services/references.js +102 -21
- package/dist/server/services/references.js.map +1 -1
- package/dist/server/services/release.d.ts +10 -10
- package/dist/server/services/release.js +32 -63
- package/dist/server/services/release.js.map +1 -1
- package/dist/server/services/section-indexer.d.ts +0 -1
- package/dist/server/services/section-indexer.js +5 -7
- package/dist/server/services/section-indexer.js.map +1 -1
- package/dist/server/services/skill-registry.d.ts +28 -1
- package/dist/server/services/skill-registry.js +51 -10
- package/dist/server/services/skill-registry.js.map +1 -1
- package/dist/server/services/static-html.d.ts +24 -0
- package/dist/server/services/static-html.js +49 -0
- package/dist/server/services/static-html.js.map +1 -0
- package/dist/server/services/tags.d.ts +13 -3
- package/dist/server/services/tags.js +65 -26
- package/dist/server/services/tags.js.map +1 -1
- package/dist/server/services/versions.d.ts +7 -7
- package/dist/server/services/versions.js +34 -37
- package/dist/server/services/versions.js.map +1 -1
- package/dist/shared/entities.d.ts +2 -2
- package/dist/shared/types.d.ts +9 -0
- package/dist/shared/xml-tags.d.ts +8 -0
- package/dist/shared/xml-tags.js +24 -0
- package/dist/shared/xml-tags.js.map +1 -1
- package/package.json +1 -1
- package/dist/client/assets/channel-BqjILLUr.js +0 -1
- package/dist/client/assets/classDiagram-4FO5ZUOK-LjT84-kK.js +0 -1
- package/dist/client/assets/classDiagram-v2-Q7XG4LA2-LjT84-kK.js +0 -1
- package/dist/client/assets/stateDiagram-v2-BHNVJYJU-C6-8M5Sb.js +0 -1
- package/dist/server/db/migrations/026_ac_seed.sql +0 -75
|
@@ -0,0 +1,179 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* M29 EntityIndexerService — rebuilds the derived SQLite index from the
|
|
3
|
+
* committed entity files. Hybrid SQLite-primary indexer modelled on
|
|
4
|
+
* SectionIndexerService (M06): queries go to the DB, no in-memory map.
|
|
5
|
+
*
|
|
6
|
+
* - indexAll() full rebuild at boot, dependency-ordered (tags.json →
|
|
7
|
+
* dto/database-table/ui-view/ac → endpoint). Awaited BEFORE
|
|
8
|
+
* app.listen(); does NOT broadcast (no client connected).
|
|
9
|
+
* - schedulePage() debounced (300ms) incremental reindex of one file on watch.
|
|
10
|
+
* - handleUnlink() remove the row + junction cascades, broadcast delete.
|
|
11
|
+
*
|
|
12
|
+
* Restore goes through the index path: HostEntityWriter(capture=false) so the
|
|
13
|
+
* rebuild does NOT write entity_version rows (the boot acceptance criterion) and
|
|
14
|
+
* service mutations run with writeFile=false (never re-write the files we read).
|
|
15
|
+
*/
|
|
16
|
+
import { HostEntityWriter } from './entity-writer.js';
|
|
17
|
+
/** dto/table/ui-view/ac before endpoint (endpoint_dto FK needs dto rows first). */
|
|
18
|
+
const DEP_ORDER = ['dto', 'database-table', 'ui-view', 'ac', 'endpoint'];
|
|
19
|
+
const ENTITY_TABLE = {
|
|
20
|
+
endpoint: 'endpoint',
|
|
21
|
+
dto: 'dto',
|
|
22
|
+
'database-table': 'database_table',
|
|
23
|
+
'ui-view': 'ui_view',
|
|
24
|
+
ac: 'ac',
|
|
25
|
+
};
|
|
26
|
+
export class EntityIndexerService {
|
|
27
|
+
db;
|
|
28
|
+
store;
|
|
29
|
+
watcher;
|
|
30
|
+
ws;
|
|
31
|
+
host;
|
|
32
|
+
tags;
|
|
33
|
+
reader;
|
|
34
|
+
debounceMs = 300;
|
|
35
|
+
pending = new Map();
|
|
36
|
+
constructor(db, store, watcher, ws, host, tags, reader) {
|
|
37
|
+
this.db = db;
|
|
38
|
+
this.store = store;
|
|
39
|
+
this.watcher = watcher;
|
|
40
|
+
this.ws = ws;
|
|
41
|
+
this.host = host;
|
|
42
|
+
this.tags = tags;
|
|
43
|
+
this.reader = reader;
|
|
44
|
+
}
|
|
45
|
+
// ─── index-path restore (no version capture, no file writes) ──────────────
|
|
46
|
+
indexCtx() {
|
|
47
|
+
return {
|
|
48
|
+
reader: this.reader,
|
|
49
|
+
writer: new HostEntityWriter(this.host, this.tags, { capture: false }),
|
|
50
|
+
releaseId: null,
|
|
51
|
+
actor: 'user',
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
// ─── boot full rebuild ────────────────────────────────────────────────────
|
|
55
|
+
async indexAll() {
|
|
56
|
+
// Clear the derived entity/tag/junction tables (children before parents),
|
|
57
|
+
// then rebuild from the files. entity_version (the log) and
|
|
58
|
+
// section_entity_link (derived from pages) are NOT cleared.
|
|
59
|
+
this.db
|
|
60
|
+
.transaction(() => {
|
|
61
|
+
this.db.exec(`DELETE FROM entity_tag;
|
|
62
|
+
DELETE FROM endpoint_dto;
|
|
63
|
+
DELETE FROM endpoint;
|
|
64
|
+
DELETE FROM dto;
|
|
65
|
+
DELETE FROM database_table;
|
|
66
|
+
DELETE FROM ui_view;
|
|
67
|
+
DELETE FROM ac;
|
|
68
|
+
DELETE FROM tag;`);
|
|
69
|
+
})();
|
|
70
|
+
this.indexTagsFile(); // tags first — so entity tag refs resolve to real rows
|
|
71
|
+
let count = 0;
|
|
72
|
+
for (const type of DEP_ORDER) {
|
|
73
|
+
if (!this.host.getEntity(type))
|
|
74
|
+
continue; // inactive type → files kept, not indexed
|
|
75
|
+
for (const slug of this.store.listType(type)) {
|
|
76
|
+
if (this.indexEntity(type, slug, false))
|
|
77
|
+
count += 1;
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
console.log(`[entity-indexer] indexed ${count} entities from ${this.store.root}`);
|
|
81
|
+
}
|
|
82
|
+
// ─── incremental (file-watch) ─────────────────────────────────────────────
|
|
83
|
+
schedulePage(relPath) {
|
|
84
|
+
const prev = this.pending.get(relPath);
|
|
85
|
+
if (prev)
|
|
86
|
+
clearTimeout(prev);
|
|
87
|
+
const timer = setTimeout(() => {
|
|
88
|
+
this.pending.delete(relPath);
|
|
89
|
+
try {
|
|
90
|
+
this.indexFromWatch(relPath);
|
|
91
|
+
}
|
|
92
|
+
catch (err) {
|
|
93
|
+
console.error(`[entity-indexer] failed to index ${relPath}:`, err);
|
|
94
|
+
}
|
|
95
|
+
}, this.debounceMs);
|
|
96
|
+
this.pending.set(relPath, timer);
|
|
97
|
+
}
|
|
98
|
+
async handleUnlink(relPath) {
|
|
99
|
+
const prev = this.pending.get(relPath);
|
|
100
|
+
if (prev) {
|
|
101
|
+
clearTimeout(prev);
|
|
102
|
+
this.pending.delete(relPath);
|
|
103
|
+
}
|
|
104
|
+
if (this.store.isTagsFile(relPath)) {
|
|
105
|
+
// A true tags.json unlink is degenerate; do NOT mass-delete tags (would
|
|
106
|
+
// cascade entity_tag). Keep the current tag index; warn.
|
|
107
|
+
console.warn('[entity-indexer] tags.json unlinked — keeping tag index');
|
|
108
|
+
return;
|
|
109
|
+
}
|
|
110
|
+
const parsed = this.store.parseRelPath(relPath);
|
|
111
|
+
if (!parsed)
|
|
112
|
+
return;
|
|
113
|
+
const { type, slug } = parsed;
|
|
114
|
+
this.db
|
|
115
|
+
.transaction(() => {
|
|
116
|
+
this.db
|
|
117
|
+
.prepare(`DELETE FROM entity_tag WHERE entity_type = ? AND entity_slug = ?`)
|
|
118
|
+
.run(type, slug);
|
|
119
|
+
// endpoint_dto rows cascade via FK ON DELETE CASCADE.
|
|
120
|
+
this.db.prepare(`DELETE FROM ${ENTITY_TABLE[type]} WHERE slug = ?`).run(slug);
|
|
121
|
+
})();
|
|
122
|
+
this.ws.broadcast({ kind: 'entity:indexed', type, slug, op: 'delete' });
|
|
123
|
+
}
|
|
124
|
+
indexFromWatch(relPath) {
|
|
125
|
+
if (this.store.isTagsFile(relPath)) {
|
|
126
|
+
this.indexTagsFile();
|
|
127
|
+
this.ws.broadcast({ kind: 'tag:changed', slug: '' });
|
|
128
|
+
return;
|
|
129
|
+
}
|
|
130
|
+
const parsed = this.store.parseRelPath(relPath);
|
|
131
|
+
if (!parsed)
|
|
132
|
+
return;
|
|
133
|
+
if (this.indexEntity(parsed.type, parsed.slug, true)) {
|
|
134
|
+
// broadcast handled inside indexEntity when reindex succeeds
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
// ─── single-entity reindex ────────────────────────────────────────────────
|
|
138
|
+
/** Returns true if the entity was (re)indexed; false if skipped (inactive/error). */
|
|
139
|
+
indexEntity(type, slug, broadcast) {
|
|
140
|
+
if (!this.host.getEntity(type))
|
|
141
|
+
return false; // inactive type
|
|
142
|
+
let snap;
|
|
143
|
+
try {
|
|
144
|
+
snap = this.store.read(type, slug);
|
|
145
|
+
}
|
|
146
|
+
catch (err) {
|
|
147
|
+
console.warn(`[entity-indexer] skip ${type}/${slug}: ${err.message}`);
|
|
148
|
+
return false;
|
|
149
|
+
}
|
|
150
|
+
try {
|
|
151
|
+
this.host.restore(type, snap, this.indexCtx());
|
|
152
|
+
}
|
|
153
|
+
catch (err) {
|
|
154
|
+
console.warn(`[entity-indexer] restore failed ${type}/${slug}: ${err.message}`);
|
|
155
|
+
return false;
|
|
156
|
+
}
|
|
157
|
+
if (broadcast)
|
|
158
|
+
this.ws.broadcast({ kind: 'entity:indexed', type, slug, op: 'upsert' });
|
|
159
|
+
return true;
|
|
160
|
+
}
|
|
161
|
+
indexTagsFile() {
|
|
162
|
+
let tags;
|
|
163
|
+
try {
|
|
164
|
+
tags = this.store.readTags();
|
|
165
|
+
}
|
|
166
|
+
catch (err) {
|
|
167
|
+
console.warn(`[entity-indexer] tags.json parse failed: ${err.message}`);
|
|
168
|
+
return;
|
|
169
|
+
}
|
|
170
|
+
const upsert = this.db.prepare(`INSERT INTO tag (slug, name, color, description) VALUES (?, ?, ?, ?)
|
|
171
|
+
ON CONFLICT(slug) DO UPDATE SET name = excluded.name, color = excluded.color, description = excluded.description`);
|
|
172
|
+
this.db
|
|
173
|
+
.transaction(() => {
|
|
174
|
+
for (const t of tags)
|
|
175
|
+
upsert.run(t.slug, t.name, t.color ?? null, t.description ?? null);
|
|
176
|
+
})();
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
//# sourceMappingURL=entity-indexer.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"entity-indexer.js","sourceRoot":"","sources":["../../../src/server/services/entity-indexer.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* M29 Entity Store — the file layer that makes entities git-committed text.
|
|
3
|
+
*
|
|
4
|
+
* Each entity = one JSON file `<entitiesDir>/<type>/<slug>.json`; tag
|
|
5
|
+
* definitions = `<entitiesDir>/tags.json`. These files are the SOURCE OF TRUTH;
|
|
6
|
+
* SQLite is a derived index rebuilt from them at boot (see EntityIndexerService).
|
|
7
|
+
*
|
|
8
|
+
* File content = `host.snapshot(row)` run through `canonicalize` so two writes
|
|
9
|
+
* of an unchanged entity are byte-identical (the determinism invariant — any
|
|
10
|
+
* non-deterministic field would produce git-diff noise on every rebuild).
|
|
11
|
+
*
|
|
12
|
+
* Writes are atomic (temp→rename) and `suppress()` the dedicated entities
|
|
13
|
+
* watcher so a programmatic write does not trigger its own reindex.
|
|
14
|
+
*/
|
|
15
|
+
import type { PluginHost } from '../core/plugin-host/types.js';
|
|
16
|
+
import { type RawEntityReader, type RawEntityType } from '../domain/raw-entity-reader.js';
|
|
17
|
+
import type { SnapshotData } from '../serialization/types.js';
|
|
18
|
+
import type { EntitiesWatcher } from '../fs/entities-watcher.js';
|
|
19
|
+
/** Tag definition as stored in tags.json (registry source of truth). */
|
|
20
|
+
export interface TagSnapshot {
|
|
21
|
+
slug: string;
|
|
22
|
+
name: string;
|
|
23
|
+
color: string | null;
|
|
24
|
+
description: string | null;
|
|
25
|
+
}
|
|
26
|
+
export interface EntityStoreFile {
|
|
27
|
+
type: RawEntityType;
|
|
28
|
+
slug: string;
|
|
29
|
+
relPath: string;
|
|
30
|
+
}
|
|
31
|
+
export declare class EntityStore {
|
|
32
|
+
private watcher;
|
|
33
|
+
private reader;
|
|
34
|
+
private host;
|
|
35
|
+
readonly root: string;
|
|
36
|
+
constructor(cwd: string, entitiesDir: string, watcher: EntitiesWatcher, reader: RawEntityReader, host: PluginHost);
|
|
37
|
+
relPathFor(type: RawEntityType, slug: string): string;
|
|
38
|
+
/** Invert a relPath → {type, slug}; null if it is not an active-type entity file. */
|
|
39
|
+
parseRelPath(relPath: string): {
|
|
40
|
+
type: RawEntityType;
|
|
41
|
+
slug: string;
|
|
42
|
+
} | null;
|
|
43
|
+
isTagsFile(relPath: string): boolean;
|
|
44
|
+
private absFor;
|
|
45
|
+
ensureRoot(): void;
|
|
46
|
+
exists(type: RawEntityType, slug: string): boolean;
|
|
47
|
+
/** Parse `<type>/<slug>.json`. Throws on ENOENT or invalid JSON (caller decides). */
|
|
48
|
+
read(type: RawEntityType, slug: string): SnapshotData;
|
|
49
|
+
readRel(relPath: string): SnapshotData;
|
|
50
|
+
/** Write a snapshot to `<type>/<slug>.json` (atomic + suppress). */
|
|
51
|
+
write(type: RawEntityType, slug: string, data: SnapshotData): void;
|
|
52
|
+
private writeRel;
|
|
53
|
+
/** Remove `<type>/<slug>.json` (atomic suppress; ignore if already gone). */
|
|
54
|
+
remove(type: RawEntityType, slug: string): void;
|
|
55
|
+
listType(type: RawEntityType): string[];
|
|
56
|
+
listAll(): EntityStoreFile[];
|
|
57
|
+
readTags(): TagSnapshot[];
|
|
58
|
+
writeTags(tags: TagSnapshot[]): void;
|
|
59
|
+
/**
|
|
60
|
+
* Snapshot the entity's CURRENT index row and write its file. The snapshot is
|
|
61
|
+
* derived via `host.snapshot` (the single source of snapshot truth) so the
|
|
62
|
+
* file always equals what a rebuild would produce. Called by services after a
|
|
63
|
+
* committed mutation, and by the boot DB→text export.
|
|
64
|
+
*/
|
|
65
|
+
persist(type: RawEntityType, slug: string): void;
|
|
66
|
+
/** Read the full tag registry from the index and write tags.json. */
|
|
67
|
+
persistTags(): void;
|
|
68
|
+
}
|
|
@@ -0,0 +1,162 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* M29 Entity Store — the file layer that makes entities git-committed text.
|
|
3
|
+
*
|
|
4
|
+
* Each entity = one JSON file `<entitiesDir>/<type>/<slug>.json`; tag
|
|
5
|
+
* definitions = `<entitiesDir>/tags.json`. These files are the SOURCE OF TRUTH;
|
|
6
|
+
* SQLite is a derived index rebuilt from them at boot (see EntityIndexerService).
|
|
7
|
+
*
|
|
8
|
+
* File content = `host.snapshot(row)` run through `canonicalize` so two writes
|
|
9
|
+
* of an unchanged entity are byte-identical (the determinism invariant — any
|
|
10
|
+
* non-deterministic field would produce git-diff noise on every rebuild).
|
|
11
|
+
*
|
|
12
|
+
* Writes are atomic (temp→rename) and `suppress()` the dedicated entities
|
|
13
|
+
* watcher so a programmatic write does not trigger its own reindex.
|
|
14
|
+
*/
|
|
15
|
+
import fs from 'node:fs';
|
|
16
|
+
import path from 'node:path';
|
|
17
|
+
import { isRawEntityType, } from '../domain/raw-entity-reader.js';
|
|
18
|
+
import { canonicalize } from '../serialization/snapshot.js';
|
|
19
|
+
import { DomainError } from './tags.js';
|
|
20
|
+
const ENTITY_TYPE_DIRS = ['endpoint', 'dto', 'database-table', 'ui-view', 'ac'];
|
|
21
|
+
const TAGS_FILE = 'tags.json';
|
|
22
|
+
const KEBAB_RE = /^[a-z0-9]+(?:-[a-z0-9]+)*$/;
|
|
23
|
+
export class EntityStore {
|
|
24
|
+
watcher;
|
|
25
|
+
reader;
|
|
26
|
+
host;
|
|
27
|
+
root;
|
|
28
|
+
constructor(cwd, entitiesDir, watcher, reader, host) {
|
|
29
|
+
this.watcher = watcher;
|
|
30
|
+
this.reader = reader;
|
|
31
|
+
this.host = host;
|
|
32
|
+
this.root = path.resolve(cwd, entitiesDir);
|
|
33
|
+
}
|
|
34
|
+
// ─── paths ────────────────────────────────────────────────────────────────
|
|
35
|
+
relPathFor(type, slug) {
|
|
36
|
+
return `${type}/${slug}.json`;
|
|
37
|
+
}
|
|
38
|
+
/** Invert a relPath → {type, slug}; null if it is not an active-type entity file. */
|
|
39
|
+
parseRelPath(relPath) {
|
|
40
|
+
const norm = relPath.replaceAll('\\', '/');
|
|
41
|
+
const m = /^([a-z-]+)\/([^/]+)\.json$/.exec(norm);
|
|
42
|
+
if (!m)
|
|
43
|
+
return null;
|
|
44
|
+
const [, type, slug] = m;
|
|
45
|
+
if (!type || !slug || !isRawEntityType(type))
|
|
46
|
+
return null;
|
|
47
|
+
return { type, slug };
|
|
48
|
+
}
|
|
49
|
+
isTagsFile(relPath) {
|
|
50
|
+
return relPath.replaceAll('\\', '/') === TAGS_FILE;
|
|
51
|
+
}
|
|
52
|
+
absFor(relPath) {
|
|
53
|
+
if (!relPath || relPath.includes('\0'))
|
|
54
|
+
throw new DomainError('VALIDATION', 'invalid path');
|
|
55
|
+
const abs = path.resolve(this.root, relPath);
|
|
56
|
+
const rel = path.relative(this.root, abs);
|
|
57
|
+
if (rel.startsWith('..') || path.isAbsolute(rel)) {
|
|
58
|
+
throw new DomainError('VALIDATION', `path escapes entities root: ${relPath}`);
|
|
59
|
+
}
|
|
60
|
+
return abs;
|
|
61
|
+
}
|
|
62
|
+
// ─── lifecycle ──────────────────────────────────────────────────────────
|
|
63
|
+
ensureRoot() {
|
|
64
|
+
fs.mkdirSync(this.root, { recursive: true });
|
|
65
|
+
}
|
|
66
|
+
// ─── entity JSON ──────────────────────────────────────────────────────────
|
|
67
|
+
exists(type, slug) {
|
|
68
|
+
return fs.existsSync(this.absFor(this.relPathFor(type, slug)));
|
|
69
|
+
}
|
|
70
|
+
/** Parse `<type>/<slug>.json`. Throws on ENOENT or invalid JSON (caller decides). */
|
|
71
|
+
read(type, slug) {
|
|
72
|
+
return this.readRel(this.relPathFor(type, slug));
|
|
73
|
+
}
|
|
74
|
+
readRel(relPath) {
|
|
75
|
+
const raw = fs.readFileSync(this.absFor(relPath), 'utf-8');
|
|
76
|
+
return JSON.parse(raw);
|
|
77
|
+
}
|
|
78
|
+
/** Write a snapshot to `<type>/<slug>.json` (atomic + suppress). */
|
|
79
|
+
write(type, slug, data) {
|
|
80
|
+
if (!KEBAB_RE.test(slug)) {
|
|
81
|
+
throw new DomainError('VALIDATION', `slug '${slug}' is not kebab-case`);
|
|
82
|
+
}
|
|
83
|
+
this.writeRel(this.relPathFor(type, slug), data);
|
|
84
|
+
}
|
|
85
|
+
writeRel(relPath, data) {
|
|
86
|
+
const abs = this.absFor(relPath);
|
|
87
|
+
fs.mkdirSync(path.dirname(abs), { recursive: true });
|
|
88
|
+
const body = JSON.stringify(canonicalize(data), null, 2) + '\n';
|
|
89
|
+
this.watcher.suppress(relPath);
|
|
90
|
+
const tmp = `${abs}.tmp`;
|
|
91
|
+
fs.writeFileSync(tmp, body);
|
|
92
|
+
fs.renameSync(tmp, abs);
|
|
93
|
+
}
|
|
94
|
+
/** Remove `<type>/<slug>.json` (atomic suppress; ignore if already gone). */
|
|
95
|
+
remove(type, slug) {
|
|
96
|
+
const relPath = this.relPathFor(type, slug);
|
|
97
|
+
this.watcher.suppress(relPath);
|
|
98
|
+
try {
|
|
99
|
+
fs.unlinkSync(this.absFor(relPath));
|
|
100
|
+
}
|
|
101
|
+
catch (err) {
|
|
102
|
+
if (err.code !== 'ENOENT')
|
|
103
|
+
throw err;
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
listType(type) {
|
|
107
|
+
const dir = path.join(this.root, type);
|
|
108
|
+
if (!fs.existsSync(dir))
|
|
109
|
+
return [];
|
|
110
|
+
return fs
|
|
111
|
+
.readdirSync(dir)
|
|
112
|
+
.filter((f) => f.endsWith('.json') && !f.startsWith('.'))
|
|
113
|
+
.map((f) => f.slice(0, -'.json'.length))
|
|
114
|
+
.sort();
|
|
115
|
+
}
|
|
116
|
+
listAll() {
|
|
117
|
+
const out = [];
|
|
118
|
+
for (const type of ENTITY_TYPE_DIRS) {
|
|
119
|
+
for (const slug of this.listType(type)) {
|
|
120
|
+
out.push({ type, slug, relPath: this.relPathFor(type, slug) });
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
return out;
|
|
124
|
+
}
|
|
125
|
+
// ─── tags.json ──────────────────────────────────────────────────────────
|
|
126
|
+
readTags() {
|
|
127
|
+
const abs = path.join(this.root, TAGS_FILE);
|
|
128
|
+
if (!fs.existsSync(abs))
|
|
129
|
+
return [];
|
|
130
|
+
const parsed = JSON.parse(fs.readFileSync(abs, 'utf-8'));
|
|
131
|
+
return Array.isArray(parsed) ? parsed : [];
|
|
132
|
+
}
|
|
133
|
+
writeTags(tags) {
|
|
134
|
+
const sorted = [...tags].sort((a, b) => a.slug.localeCompare(b.slug));
|
|
135
|
+
this.writeRel(TAGS_FILE, sorted);
|
|
136
|
+
}
|
|
137
|
+
// ─── derive-from-index helpers (write-path + boot export) ─────────────────
|
|
138
|
+
/**
|
|
139
|
+
* Snapshot the entity's CURRENT index row and write its file. The snapshot is
|
|
140
|
+
* derived via `host.snapshot` (the single source of snapshot truth) so the
|
|
141
|
+
* file always equals what a rebuild would produce. Called by services after a
|
|
142
|
+
* committed mutation, and by the boot DB→text export.
|
|
143
|
+
*/
|
|
144
|
+
persist(type, slug) {
|
|
145
|
+
const entity = this.reader.getEntity(type, slug);
|
|
146
|
+
if (!entity)
|
|
147
|
+
throw new DomainError('NOT_FOUND', `${type} '${slug}' not found for persist`);
|
|
148
|
+
const snap = this.host.snapshot(type, entity, { reader: this.reader, depth: 0, maxDepth: 1 });
|
|
149
|
+
this.write(type, slug, snap);
|
|
150
|
+
}
|
|
151
|
+
/** Read the full tag registry from the index and write tags.json. */
|
|
152
|
+
persistTags() {
|
|
153
|
+
const tags = this.reader.listTags().map((t) => ({
|
|
154
|
+
slug: t.slug,
|
|
155
|
+
name: t.name,
|
|
156
|
+
color: t.color,
|
|
157
|
+
description: t.description,
|
|
158
|
+
}));
|
|
159
|
+
this.writeTags(tags);
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
//# sourceMappingURL=entity-store.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"entity-store.js","sourceRoot":"","sources":["../../../src/server/services/entity-store.ts"],"names":[],"mappings":"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"}
|
|
@@ -23,7 +23,18 @@ import type { TagsService } from './tags.js';
|
|
|
23
23
|
export declare class HostEntityWriter implements EntityWriter {
|
|
24
24
|
private host;
|
|
25
25
|
private tags;
|
|
26
|
-
|
|
26
|
+
/**
|
|
27
|
+
* M29: `capture` gates `entity_version` capture inside the service mutation.
|
|
28
|
+
* - index-reconstruction path (boot rebuild / reindex): capture=false
|
|
29
|
+
* - M17 release restore: capture=true (a real mutation, append-only)
|
|
30
|
+
* `writeFile` is ALWAYS false here: the restore path must never write entity
|
|
31
|
+
* files inside the service (the index rebuild reads files; release restore
|
|
32
|
+
* persists each entity's file once at the end, after junctions are synced).
|
|
33
|
+
*/
|
|
34
|
+
private readonly mutateOpts;
|
|
35
|
+
constructor(host: PluginHost, tags: TagsService, opts?: {
|
|
36
|
+
capture?: boolean;
|
|
37
|
+
});
|
|
27
38
|
upsertEndpoint(slug: string, input: Parameters<EndpointService['upsert']>[1], actor: ChangedBy): UpsertResult<ReturnType<EndpointService['upsert']>['entity']>;
|
|
28
39
|
upsertDto(slug: string, input: Parameters<DtoService['upsert']>[1], actor: ChangedBy): UpsertResult<ReturnType<DtoService['upsert']>['dto']>;
|
|
29
40
|
upsertDatabaseTable(slug: string, input: Parameters<DatabaseTableService['upsert']>[1], actor: ChangedBy): UpsertResult<ReturnType<DatabaseTableService['upsert']>['dbTable']>;
|
|
@@ -14,33 +14,43 @@ import { DomainError } from './tags.js';
|
|
|
14
14
|
export class HostEntityWriter {
|
|
15
15
|
host;
|
|
16
16
|
tags;
|
|
17
|
-
|
|
17
|
+
/**
|
|
18
|
+
* M29: `capture` gates `entity_version` capture inside the service mutation.
|
|
19
|
+
* - index-reconstruction path (boot rebuild / reindex): capture=false
|
|
20
|
+
* - M17 release restore: capture=true (a real mutation, append-only)
|
|
21
|
+
* `writeFile` is ALWAYS false here: the restore path must never write entity
|
|
22
|
+
* files inside the service (the index rebuild reads files; release restore
|
|
23
|
+
* persists each entity's file once at the end, after junctions are synced).
|
|
24
|
+
*/
|
|
25
|
+
mutateOpts;
|
|
26
|
+
constructor(host, tags, opts = {}) {
|
|
18
27
|
this.host = host;
|
|
19
28
|
this.tags = tags;
|
|
29
|
+
this.mutateOpts = { capture: opts.capture ?? true, writeFile: false };
|
|
20
30
|
}
|
|
21
31
|
upsertEndpoint(slug, input, actor) {
|
|
22
32
|
const service = this.requireService('endpoint');
|
|
23
|
-
const result = service.upsert(slug, input, actor);
|
|
33
|
+
const result = service.upsert(slug, input, actor, this.mutateOpts);
|
|
24
34
|
return { entity: result.entity, op: result.op };
|
|
25
35
|
}
|
|
26
36
|
upsertDto(slug, input, actor) {
|
|
27
37
|
const service = this.requireService('dto');
|
|
28
|
-
const result = service.upsert(slug, input, actor);
|
|
38
|
+
const result = service.upsert(slug, input, actor, this.mutateOpts);
|
|
29
39
|
return { entity: result.dto, op: result.op };
|
|
30
40
|
}
|
|
31
41
|
upsertDatabaseTable(slug, input, actor) {
|
|
32
42
|
const service = this.requireService('database-table');
|
|
33
|
-
const result = service.upsert(slug, input, actor);
|
|
43
|
+
const result = service.upsert(slug, input, actor, this.mutateOpts);
|
|
34
44
|
return { entity: result.dbTable, op: result.op, warnings: result.warnings };
|
|
35
45
|
}
|
|
36
46
|
upsertUiView(slug, input, actor) {
|
|
37
47
|
const service = this.requireService('ui-view');
|
|
38
|
-
const result = service.upsert(slug, input, actor);
|
|
48
|
+
const result = service.upsert(slug, input, actor, this.mutateOpts);
|
|
39
49
|
return { entity: result.uiView, op: result.op, warnings: result.warnings };
|
|
40
50
|
}
|
|
41
51
|
upsertAc(slug, input, actor) {
|
|
42
52
|
const service = this.requireService('ac');
|
|
43
|
-
const result = service.upsert(slug, input, actor);
|
|
53
|
+
const result = service.upsert(slug, input, actor, this.mutateOpts);
|
|
44
54
|
return { entity: result.ac, op: result.op };
|
|
45
55
|
}
|
|
46
56
|
syncEndpointDtos(endpointSlug, target) {
|
|
@@ -58,7 +68,7 @@ export class HostEntityWriter {
|
|
|
58
68
|
for (const [k, current] of currentSet) {
|
|
59
69
|
if (!targetSet.has(k)) {
|
|
60
70
|
try {
|
|
61
|
-
service.unlinkDto(endpointSlug, current.dtoSlug, current.relation, current.statusCode);
|
|
71
|
+
service.unlinkDto(endpointSlug, current.dtoSlug, current.relation, current.statusCode, { writeFile: false });
|
|
62
72
|
unlinked += 1;
|
|
63
73
|
}
|
|
64
74
|
catch (err) {
|
|
@@ -70,7 +80,7 @@ export class HostEntityWriter {
|
|
|
70
80
|
for (const [k, want] of targetSet) {
|
|
71
81
|
if (!currentSet.has(k)) {
|
|
72
82
|
try {
|
|
73
|
-
service.linkDto(endpointSlug, want.dtoSlug, want.relation, want.statusCode);
|
|
83
|
+
service.linkDto(endpointSlug, want.dtoSlug, want.relation, want.statusCode, { writeFile: false });
|
|
74
84
|
linked += 1;
|
|
75
85
|
}
|
|
76
86
|
catch (err) {
|
|
@@ -81,10 +91,11 @@ export class HostEntityWriter {
|
|
|
81
91
|
return { linked, unlinked, warnings };
|
|
82
92
|
}
|
|
83
93
|
syncTags(type, slug, tags) {
|
|
84
|
-
|
|
85
|
-
|
|
94
|
+
// M29: slug is the sole identity — assign directly. The caller's upsert has
|
|
95
|
+
// already ensured the entity row exists.
|
|
96
|
+
if (!this.host.entityExists(type, slug))
|
|
86
97
|
return;
|
|
87
|
-
this.tags.assignTags(type,
|
|
98
|
+
this.tags.assignTags(type, slug, tags);
|
|
88
99
|
}
|
|
89
100
|
delete(type, slug, actor) {
|
|
90
101
|
switch (type) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"entity-writer.js","sourceRoot":"","sources":["../../../src/server/services/entity-writer.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAgBH,OAAO,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AAExC,MAAM,OAAO,gBAAgB;
|
|
1
|
+
{"version":3,"file":"entity-writer.js","sourceRoot":"","sources":["../../../src/server/services/entity-writer.ts"],"names":[],"mappings":"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"}
|
|
@@ -91,8 +91,13 @@ export class GitService {
|
|
|
91
91
|
// worktree). `git add` matches pathspecs lexically against the real worktree
|
|
92
92
|
// root, so an unresolved symlink path reads as "outside repository". Resolve
|
|
93
93
|
// to real paths and keep only those that actually live inside `root`.
|
|
94
|
+
//
|
|
95
|
+
// M29: also stage the committed entity store (<entitiesDir> contains the
|
|
96
|
+
// entity JSON files + tags.json — the source of truth). db.sqlite is
|
|
97
|
+
// gitignored, so the whole dir can be staged safely.
|
|
98
|
+
const entitiesPath = path.resolve(this.cwd, readConfig(this.cwd).entitiesDir);
|
|
94
99
|
const targets = [];
|
|
95
|
-
for (const p of [this.pagesPath, configPath(this.cwd)]) {
|
|
100
|
+
for (const p of [this.pagesPath, configPath(this.cwd), entitiesPath]) {
|
|
96
101
|
let real;
|
|
97
102
|
try {
|
|
98
103
|
real = fs.realpathSync(p);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"git.js","sourceRoot":"","sources":["../../../src/server/services/git.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"git.js","sourceRoot":"","sources":["../../../src/server/services/git.ts"],"names":[],"mappings":"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"}
|
|
@@ -135,7 +135,11 @@ export class PagesService {
|
|
|
135
135
|
nodes.push({ type: 'folder', name: entry.name, path: rel, children });
|
|
136
136
|
}
|
|
137
137
|
else if (entry.isFile() && entry.name.endsWith('.md')) {
|
|
138
|
-
nodes.push({ type: 'file', name: entry.name, path: rel });
|
|
138
|
+
nodes.push({ type: 'file', name: entry.name, path: rel, fileType: 'markdown' });
|
|
139
|
+
}
|
|
140
|
+
else if (entry.isFile() && entry.name.endsWith('.html')) {
|
|
141
|
+
// M30: .html files are read-only previews served via /api/static/*.
|
|
142
|
+
nodes.push({ type: 'file', name: entry.name, path: rel, fileType: 'html' });
|
|
139
143
|
}
|
|
140
144
|
}
|
|
141
145
|
nodes.sort((a, b) => {
|