@sporhq/spor 0.5.0 → 0.5.1
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/.claude-plugin/plugin.json +1 -1
- package/bin/spor.js +33 -16
- package/package.json +1 -1
|
@@ -2,6 +2,6 @@
|
|
|
2
2
|
"name": "spor",
|
|
3
3
|
"displayName": "Spor Context Compiler",
|
|
4
4
|
"description": "Maintains a typed, versioned knowledge graph and compiles compact briefings from it: session-start injection, per-prompt relevance digests, capture at discovery, end-of-session distillation, decision queue.",
|
|
5
|
-
"version": "0.5.
|
|
5
|
+
"version": "0.5.1",
|
|
6
6
|
"author": { "name": "losthammer" }
|
|
7
7
|
}
|
package/bin/spor.js
CHANGED
|
@@ -450,6 +450,27 @@ async function cmdCompile(cfg, verb, args) {
|
|
|
450
450
|
return passthrough("compile.js", compileArgs);
|
|
451
451
|
}
|
|
452
452
|
|
|
453
|
+
// Compile a node's remote briefing the way the /spor:brief skill does: the raw
|
|
454
|
+
// node (GET /v1/nodes/<id>) plus a title/summary-seeded /v1/digest for its
|
|
455
|
+
// neighborhood, concatenated. Shared by compileRemote (brief / compile --root)
|
|
456
|
+
// and compileBriefing (dispatch) so the two can't drift — dispatch used to
|
|
457
|
+
// embed only the bare node, a thinner standing context than an interactive
|
|
458
|
+
// brief (issue-spor-dispatch-briefing-omits-neighborhood). Returns
|
|
459
|
+
// {transport,error} | {ok:false,status} | {ok:true,status,text}; the
|
|
460
|
+
// neighborhood is fail-soft (a failed/empty digest just yields the raw node).
|
|
461
|
+
async function remoteNodeBriefing(cfg, { root, project }) {
|
|
462
|
+
const r = await remote.get(cfg, `/v1/nodes/${encodeURIComponent(root)}`, { timeoutMs: 8000 });
|
|
463
|
+
if (r.transport) return { transport: true, error: r.error, text: "" };
|
|
464
|
+
if (!r.ok) return { ok: false, status: r.status, text: "" };
|
|
465
|
+
const raw = (r.json && r.json.raw) || r.text || "";
|
|
466
|
+
// Seed the neighborhood digest from the node's own title/summary (the REST
|
|
467
|
+
// /v1/digest is query-mode only — root compile is not exposed over REST).
|
|
468
|
+
const seed = (r.json && (r.json.title || r.json.summary)) || fmField(raw, "title") || fmField(raw, "summary") || root;
|
|
469
|
+
const d = await remote.post(cfg, "/v1/digest", project ? { query: seed, project } : { query: seed }, { timeoutMs: 8000 });
|
|
470
|
+
const neighborhood = d.ok && d.json && d.json.found !== false ? d.json.text || "" : "";
|
|
471
|
+
return { ok: true, status: r.status, text: neighborhood ? `${raw}\n\n${neighborhood}` : raw };
|
|
472
|
+
}
|
|
473
|
+
|
|
453
474
|
// The remote arm of compile/brief. Mirrors the /spor:brief skill's remote
|
|
454
475
|
// resolution: a node id -> the raw node plus a title/summary-seeded /v1/digest
|
|
455
476
|
// for its neighborhood; free text -> POST /v1/digest. --skeleton has no server
|
|
@@ -475,27 +496,20 @@ async function compileRemote(cfg, args) {
|
|
|
475
496
|
|
|
476
497
|
let text = "";
|
|
477
498
|
if (root) {
|
|
478
|
-
const
|
|
479
|
-
if (
|
|
480
|
-
err(`offline — could not reach server (${
|
|
499
|
+
const b = await remoteNodeBriefing(cfg, { root, project });
|
|
500
|
+
if (b.transport) {
|
|
501
|
+
err(`offline — could not reach server (${b.error})`);
|
|
481
502
|
return 1;
|
|
482
503
|
}
|
|
483
|
-
if (
|
|
504
|
+
if (b.status === 404) {
|
|
484
505
|
err(`no such node: ${root}`);
|
|
485
506
|
return 1;
|
|
486
507
|
}
|
|
487
|
-
if (!
|
|
488
|
-
err(`error ${
|
|
508
|
+
if (!b.ok) {
|
|
509
|
+
err(`error ${b.status}`);
|
|
489
510
|
return 1;
|
|
490
511
|
}
|
|
491
|
-
|
|
492
|
-
// Seed the neighborhood digest from the node's own title/summary, exactly as
|
|
493
|
-
// the /spor:brief skill does (the REST /v1/digest is query-mode only — root
|
|
494
|
-
// compile is not exposed over REST, only via the query_graph MCP tool).
|
|
495
|
-
const seed = (r.json && (r.json.title || r.json.summary)) || fmField(raw, "title") || fmField(raw, "summary") || root;
|
|
496
|
-
const d = await remote.post(cfg, "/v1/digest", project ? { query: seed, project } : { query: seed }, { timeoutMs: 8000 });
|
|
497
|
-
const neighborhood = d.ok && d.json && d.json.found !== false ? d.json.text || "" : "";
|
|
498
|
-
text = neighborhood ? `${raw}\n\n${neighborhood}` : raw;
|
|
512
|
+
text = b.text;
|
|
499
513
|
} else {
|
|
500
514
|
const body = { query };
|
|
501
515
|
if (project) body.project = project;
|
|
@@ -1535,8 +1549,11 @@ async function resolveNode(cfg, id) {
|
|
|
1535
1549
|
async function compileBriefing(cfg, { nodeId, query, full, project }) {
|
|
1536
1550
|
if (cfg.mode() === "remote") {
|
|
1537
1551
|
if (nodeId) {
|
|
1538
|
-
|
|
1539
|
-
|
|
1552
|
+
// Same raw-node + seeded-neighborhood resolution as `spor brief <id>`, so
|
|
1553
|
+
// a dispatched agent's standing context matches an interactive brief
|
|
1554
|
+
// rather than the bare node (issue-spor-dispatch-briefing-omits-neighborhood).
|
|
1555
|
+
const b = await remoteNodeBriefing(cfg, { root: nodeId, project });
|
|
1556
|
+
return b.ok ? b.text : "";
|
|
1540
1557
|
}
|
|
1541
1558
|
const r = await remote.post(cfg, "/v1/digest", project ? { query, project } : { query });
|
|
1542
1559
|
return r.ok && r.json && r.json.found !== false ? r.json.text || "" : "";
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@sporhq/spor",
|
|
3
|
-
"version": "0.5.
|
|
3
|
+
"version": "0.5.1",
|
|
4
4
|
"description": "Spor — a shared memory substrate for teams and agents. Decisions, their reasons, and the traces they leave. Knowledge-graph context compiler: session-start briefings, per-prompt digests, capture at discovery, end-of-session distillation, decision queue.",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"author": "Anthony Allen",
|