@swarmvaultai/cli 1.1.0 → 1.3.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/README.md +15 -0
- package/dist/index.js +71 -18
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -39,6 +39,8 @@ swarmvault ingest ./repo
|
|
|
39
39
|
swarmvault add https://arxiv.org/abs/2401.12345
|
|
40
40
|
swarmvault compile --max-tokens 120000
|
|
41
41
|
swarmvault diff
|
|
42
|
+
swarmvault graph share --post
|
|
43
|
+
swarmvault graph share --svg ./share-card.svg
|
|
42
44
|
swarmvault benchmark
|
|
43
45
|
swarmvault query "What keeps recurring?" --commit
|
|
44
46
|
swarmvault query "Turn this into slides" --format slides
|
|
@@ -85,6 +87,7 @@ Quick-start a scratch vault from a local directory in one command.
|
|
|
85
87
|
- initializes the current directory as a SwarmVault workspace
|
|
86
88
|
- ingests the supplied directory as local sources
|
|
87
89
|
- compiles the vault immediately
|
|
90
|
+
- writes `wiki/graph/share-card.md` and `wiki/graph/share-card.svg`, then prints both paths
|
|
88
91
|
- starts `graph serve` unless you pass `--no-serve`
|
|
89
92
|
- respects `--port` when you want a specific viewer port
|
|
90
93
|
|
|
@@ -97,6 +100,7 @@ Create a temporary sample vault with bundled sources, compile it immediately, an
|
|
|
97
100
|
- writes the demo vault under the system temp directory
|
|
98
101
|
- requires no API keys or extra setup
|
|
99
102
|
- is the fastest way to inspect the full init + ingest + compile + graph workflow on a clean machine
|
|
103
|
+
- writes `wiki/graph/share-card.md` and `wiki/graph/share-card.svg` inside the demo vault
|
|
100
104
|
- respects `--port` when you want a specific viewer port
|
|
101
105
|
|
|
102
106
|
### `swarmvault diff`
|
|
@@ -207,6 +211,7 @@ Compile the current manifests into:
|
|
|
207
211
|
- generated markdown in `wiki/`
|
|
208
212
|
- structured graph data in `state/graph.json`
|
|
209
213
|
- local search data in `state/search.sqlite`
|
|
214
|
+
- share cards at `wiki/graph/share-card.md` and `wiki/graph/share-card.svg`
|
|
210
215
|
|
|
211
216
|
The compiler also reads `swarmvault.schema.md` and records a `schema_hash` plus lifecycle metadata such as `status`, `created_at`, `updated_at`, `compiled_from`, and `managed_by` in generated pages so schema edits can mark pages stale without losing lifecycle state.
|
|
212
217
|
|
|
@@ -366,6 +371,16 @@ Inspect graph metadata, community membership, neighbors, provenance, and group-p
|
|
|
366
371
|
|
|
367
372
|
List the most connected bridge-heavy nodes in the current graph.
|
|
368
373
|
|
|
374
|
+
### `swarmvault graph share [--post] [--svg [path]]`
|
|
375
|
+
|
|
376
|
+
Print a shareable summary of the compiled graph.
|
|
377
|
+
|
|
378
|
+
- default output is the same markdown shape written to `wiki/graph/share-card.md`
|
|
379
|
+
- `--post` prints only the concise social-post text
|
|
380
|
+
- `--svg [path]` writes the 1200x630 visual share card, defaulting to `wiki/graph/share-card.svg`
|
|
381
|
+
- `--json` emits the structured share artifact for automation; with `--svg`, it also includes `svgPath`
|
|
382
|
+
- useful immediately after `swarmvault scan`, `swarmvault demo`, or a normal compile
|
|
383
|
+
|
|
369
384
|
### `swarmvault graph blast <target> [--depth <n>]`
|
|
370
385
|
|
|
371
386
|
Trace the reverse-import blast radius of changing a file or module.
|
package/dist/index.js
CHANGED
|
@@ -2,7 +2,8 @@
|
|
|
2
2
|
|
|
3
3
|
// src/index.ts
|
|
4
4
|
import { readFileSync } from "fs";
|
|
5
|
-
import { readFile as readFile2 } from "fs/promises";
|
|
5
|
+
import { mkdir as mkdir2, readFile as readFile2, writeFile as writeFile2 } from "fs/promises";
|
|
6
|
+
import path2 from "path";
|
|
6
7
|
import process2 from "process";
|
|
7
8
|
import { createInterface } from "readline/promises";
|
|
8
9
|
import {
|
|
@@ -14,6 +15,7 @@ import {
|
|
|
14
15
|
autoCommitWikiChanges,
|
|
15
16
|
benchmarkVault,
|
|
16
17
|
blastRadiusVault,
|
|
18
|
+
buildGraphShareArtifact,
|
|
17
19
|
compileVault,
|
|
18
20
|
consolidateVault,
|
|
19
21
|
createSupersessionEdge,
|
|
@@ -53,10 +55,13 @@ import {
|
|
|
53
55
|
queryGraphVault,
|
|
54
56
|
queryVault,
|
|
55
57
|
readApproval,
|
|
58
|
+
readGraphReport,
|
|
56
59
|
registerLocalWhisperProvider,
|
|
57
60
|
rejectApproval,
|
|
58
61
|
reloadManagedSources,
|
|
59
62
|
removeWatchedRoot,
|
|
63
|
+
renderGraphShareMarkdown,
|
|
64
|
+
renderGraphShareSvg,
|
|
60
65
|
resumeSourceSession,
|
|
61
66
|
reviewManagedSource,
|
|
62
67
|
reviewSourceScope,
|
|
@@ -287,9 +292,9 @@ program.name("swarmvault").description("SwarmVault is a local-first knowledge co
|
|
|
287
292
|
function readCliVersion() {
|
|
288
293
|
try {
|
|
289
294
|
const packageJson = JSON.parse(readFileSync(new URL("../package.json", import.meta.url), "utf8"));
|
|
290
|
-
return typeof packageJson.version === "string" && packageJson.version.trim() ? packageJson.version : "1.
|
|
295
|
+
return typeof packageJson.version === "string" && packageJson.version.trim() ? packageJson.version : "1.3.0";
|
|
291
296
|
} catch {
|
|
292
|
-
return "1.
|
|
297
|
+
return "1.3.0";
|
|
293
298
|
}
|
|
294
299
|
}
|
|
295
300
|
function parsePositiveInt(value, fallback) {
|
|
@@ -971,6 +976,36 @@ graph.command("export").description(
|
|
|
971
976
|
}
|
|
972
977
|
}
|
|
973
978
|
);
|
|
979
|
+
graph.command("share").description("Print a shareable summary of the compiled graph.").option("--post", "Print only the short social post text", false).option("--svg [path]", "Write the visual SVG share card, defaulting to wiki/graph/share-card.svg").action(async (options) => {
|
|
980
|
+
if (options.post && options.svg) {
|
|
981
|
+
throw new Error("Choose either --post or --svg, not both.");
|
|
982
|
+
}
|
|
983
|
+
const { paths } = await loadVaultConfig(process2.cwd());
|
|
984
|
+
const raw = await readFile2(paths.graphPath, "utf-8");
|
|
985
|
+
const graph2 = JSON.parse(raw);
|
|
986
|
+
const report = await readGraphReport(process2.cwd());
|
|
987
|
+
const artifact = buildGraphShareArtifact({
|
|
988
|
+
graph: graph2,
|
|
989
|
+
report,
|
|
990
|
+
vaultName: path2.basename(paths.rootDir)
|
|
991
|
+
});
|
|
992
|
+
if (options.svg) {
|
|
993
|
+
const svgPath = typeof options.svg === "string" ? path2.resolve(process2.cwd(), options.svg) : path2.join(paths.wikiDir, "graph", "share-card.svg");
|
|
994
|
+
await mkdir2(path2.dirname(svgPath), { recursive: true });
|
|
995
|
+
await writeFile2(svgPath, renderGraphShareSvg(artifact), "utf8");
|
|
996
|
+
if (isJson()) {
|
|
997
|
+
emitJson({ ...artifact, svgPath });
|
|
998
|
+
return;
|
|
999
|
+
}
|
|
1000
|
+
log(`Wrote SVG share card to ${svgPath}`);
|
|
1001
|
+
return;
|
|
1002
|
+
}
|
|
1003
|
+
if (isJson()) {
|
|
1004
|
+
emitJson(artifact);
|
|
1005
|
+
return;
|
|
1006
|
+
}
|
|
1007
|
+
log(options.post ? artifact.shortPost : renderGraphShareMarkdown(artifact));
|
|
1008
|
+
});
|
|
974
1009
|
graph.command("query").description("Traverse the compiled graph deterministically from local search seeds.").argument("<question>", "Question or graph search seed").option("--dfs", "Prefer a depth-first traversal instead of breadth-first", false).option("--budget <n>", "Maximum number of graph nodes to summarize").action(async (question, options) => {
|
|
975
1010
|
const budget = options.budget ? parsePositiveInt(options.budget, 0) || void 0 : void 0;
|
|
976
1011
|
const result = await queryGraphVault(process2.cwd(), question, {
|
|
@@ -1429,17 +1464,17 @@ program.command("install").description("Install SwarmVault instructions for an a
|
|
|
1429
1464
|
}
|
|
1430
1465
|
);
|
|
1431
1466
|
program.command("demo").description("Try SwarmVault with a bundled sample vault \u2014 zero config, zero API keys.").option("--port <port>", "Port for the graph viewer").option("--no-serve", "Skip launching the graph viewer after compile").action(async (options) => {
|
|
1432
|
-
const { mkdtemp, writeFile:
|
|
1467
|
+
const { mkdtemp, writeFile: writeFile3, mkdir: mkdir3 } = await import("fs/promises");
|
|
1433
1468
|
const { tmpdir } = await import("os");
|
|
1434
|
-
const
|
|
1435
|
-
const demoDir = await mkdtemp(
|
|
1469
|
+
const path3 = await import("path");
|
|
1470
|
+
const demoDir = await mkdtemp(path3.join(tmpdir(), "swarmvault-demo-"));
|
|
1436
1471
|
if (!isJson()) {
|
|
1437
1472
|
log(`Creating demo vault in ${demoDir}`);
|
|
1438
1473
|
}
|
|
1439
|
-
const rawDir =
|
|
1440
|
-
await
|
|
1441
|
-
await
|
|
1442
|
-
|
|
1474
|
+
const rawDir = path3.join(demoDir, "raw", "sources");
|
|
1475
|
+
await mkdir3(rawDir, { recursive: true });
|
|
1476
|
+
await writeFile3(
|
|
1477
|
+
path3.join(rawDir, "llm-wiki-pattern.md"),
|
|
1443
1478
|
[
|
|
1444
1479
|
"# The LLM Wiki Pattern",
|
|
1445
1480
|
"",
|
|
@@ -1467,8 +1502,8 @@ program.command("demo").description("Try SwarmVault with a bundled sample vault
|
|
|
1467
1502
|
""
|
|
1468
1503
|
].join("\n")
|
|
1469
1504
|
);
|
|
1470
|
-
await
|
|
1471
|
-
|
|
1505
|
+
await writeFile3(
|
|
1506
|
+
path3.join(rawDir, "knowledge-graphs.md"),
|
|
1472
1507
|
[
|
|
1473
1508
|
"# Knowledge Graphs for AI",
|
|
1474
1509
|
"",
|
|
@@ -1500,8 +1535,8 @@ program.command("demo").description("Try SwarmVault with a bundled sample vault
|
|
|
1500
1535
|
""
|
|
1501
1536
|
].join("\n")
|
|
1502
1537
|
);
|
|
1503
|
-
await
|
|
1504
|
-
|
|
1538
|
+
await writeFile3(
|
|
1539
|
+
path3.join(rawDir, "local-first-tools.md"),
|
|
1505
1540
|
[
|
|
1506
1541
|
"# Local-First AI Tools",
|
|
1507
1542
|
"",
|
|
@@ -1531,6 +1566,8 @@ program.command("demo").description("Try SwarmVault with a bundled sample vault
|
|
|
1531
1566
|
await ingestDirectory(demoDir, rawDir, {});
|
|
1532
1567
|
await compileVault(demoDir, {});
|
|
1533
1568
|
const { paths } = await loadVaultConfig(demoDir);
|
|
1569
|
+
const shareCardPath = path3.join(demoDir, "wiki", "graph", "share-card.md");
|
|
1570
|
+
const shareCardSvgPath = path3.join(demoDir, "wiki", "graph", "share-card.svg");
|
|
1534
1571
|
let graphStats = "";
|
|
1535
1572
|
try {
|
|
1536
1573
|
const raw = await readFile2(paths.graphPath, "utf-8");
|
|
@@ -1548,17 +1585,27 @@ program.command("demo").description("Try SwarmVault with a bundled sample vault
|
|
|
1548
1585
|
log(" 3. Generated wiki pages with cross-references and a graph report");
|
|
1549
1586
|
log("");
|
|
1550
1587
|
log(`Vault location: ${demoDir}`);
|
|
1588
|
+
log(`Share card: ${shareCardPath}`);
|
|
1589
|
+
log(`Visual card: ${shareCardSvgPath}`);
|
|
1551
1590
|
}
|
|
1552
1591
|
if (options.serve !== false) {
|
|
1553
1592
|
const port = options.port ? parsePositiveInt(options.port, 0) || void 0 : void 0;
|
|
1554
1593
|
const server = await startGraphServer(demoDir, port, { full: false });
|
|
1555
1594
|
if (isJson()) {
|
|
1556
|
-
emitJson({
|
|
1595
|
+
emitJson({
|
|
1596
|
+
demoDir,
|
|
1597
|
+
graphStats: graphStats.trim(),
|
|
1598
|
+
shareCardPath,
|
|
1599
|
+
shareCardSvgPath,
|
|
1600
|
+
port: server.port,
|
|
1601
|
+
url: `http://localhost:${server.port}`
|
|
1602
|
+
});
|
|
1557
1603
|
} else {
|
|
1558
1604
|
log(`Graph viewer running at http://localhost:${server.port}`);
|
|
1559
1605
|
log("");
|
|
1560
1606
|
log("Try next:");
|
|
1561
1607
|
log(` cd ${demoDir}`);
|
|
1608
|
+
log(" swarmvault graph share --post");
|
|
1562
1609
|
log(' swarmvault query "How does contradiction detection work?"');
|
|
1563
1610
|
log(" swarmvault lint");
|
|
1564
1611
|
}
|
|
@@ -1570,11 +1617,12 @@ program.command("demo").description("Try SwarmVault with a bundled sample vault
|
|
|
1570
1617
|
process2.exit(0);
|
|
1571
1618
|
});
|
|
1572
1619
|
} else if (isJson()) {
|
|
1573
|
-
emitJson({ demoDir, graphStats: graphStats.trim() });
|
|
1620
|
+
emitJson({ demoDir, graphStats: graphStats.trim(), shareCardPath, shareCardSvgPath });
|
|
1574
1621
|
} else {
|
|
1575
1622
|
log("");
|
|
1576
1623
|
log("Try next:");
|
|
1577
1624
|
log(` cd ${demoDir}`);
|
|
1625
|
+
log(" swarmvault graph share --post");
|
|
1578
1626
|
log(" swarmvault graph serve");
|
|
1579
1627
|
log(' swarmvault query "How does contradiction detection work?"');
|
|
1580
1628
|
}
|
|
@@ -1702,14 +1750,19 @@ program.command("scan").description("Quick-start: initialize, ingest, compile, a
|
|
|
1702
1750
|
log(`Ingested ${result.imported.length} file(s).`);
|
|
1703
1751
|
}
|
|
1704
1752
|
const compiled = await compileVault(rootDir, {});
|
|
1753
|
+
const shareCardPath = path2.join(rootDir, "wiki", "graph", "share-card.md");
|
|
1754
|
+
const shareCardSvgPath = path2.join(rootDir, "wiki", "graph", "share-card.svg");
|
|
1705
1755
|
if (!isJson()) {
|
|
1706
1756
|
log(`Compiled ${compiled.sourceCount} source(s), ${compiled.pageCount} page(s).`);
|
|
1757
|
+
log(`Share card: ${shareCardPath}`);
|
|
1758
|
+
log(`Visual card: ${shareCardSvgPath}`);
|
|
1759
|
+
log("Post text: swarmvault graph share --post");
|
|
1707
1760
|
}
|
|
1708
1761
|
if (options.serve !== false) {
|
|
1709
1762
|
const port = options.port ? parsePositiveInt(options.port, 0) || void 0 : void 0;
|
|
1710
1763
|
const server = await startGraphServer(rootDir, port, { full: false });
|
|
1711
1764
|
if (isJson()) {
|
|
1712
|
-
emitJson({ ...result, compiled, port: server.port, url: `http://localhost:${server.port}` });
|
|
1765
|
+
emitJson({ ...result, compiled, shareCardPath, shareCardSvgPath, port: server.port, url: `http://localhost:${server.port}` });
|
|
1713
1766
|
} else {
|
|
1714
1767
|
log(`Graph viewer running at http://localhost:${server.port}`);
|
|
1715
1768
|
}
|
|
@@ -1721,7 +1774,7 @@ program.command("scan").description("Quick-start: initialize, ingest, compile, a
|
|
|
1721
1774
|
process2.exit(0);
|
|
1722
1775
|
});
|
|
1723
1776
|
} else if (isJson()) {
|
|
1724
|
-
emitJson({ ...result, compiled });
|
|
1777
|
+
emitJson({ ...result, compiled, shareCardPath, shareCardSvgPath });
|
|
1725
1778
|
}
|
|
1726
1779
|
});
|
|
1727
1780
|
function enableStructuredJsonOnSubcommands(command) {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@swarmvaultai/cli",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.3.0",
|
|
4
4
|
"description": "Global CLI for SwarmVault.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/index.js",
|
|
@@ -44,7 +44,7 @@
|
|
|
44
44
|
"prepublishOnly": "node ../../scripts/check-release-sync.mjs && node ../../scripts/check-published-manifests.mjs"
|
|
45
45
|
},
|
|
46
46
|
"dependencies": {
|
|
47
|
-
"@swarmvaultai/engine": "1.
|
|
47
|
+
"@swarmvaultai/engine": "1.3.0",
|
|
48
48
|
"commander": "^14.0.1"
|
|
49
49
|
},
|
|
50
50
|
"devDependencies": {
|