@rubytech/create-maxy-code 0.1.232 → 0.1.233
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/dist/__tests__/rss-sampler-installer.test.js +27 -0
- package/dist/index.js +61 -0
- package/package.json +1 -1
- package/payload/platform/plugins/memory/PLUGIN.md +5 -1
- package/payload/platform/plugins/memory/mcp/dist/index.js +23 -7
- package/payload/platform/plugins/memory/mcp/dist/index.js.map +1 -1
- package/payload/platform/plugins/memory/mcp/dist/lib/__tests__/compiled-truth-revision.test.js +16 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/__tests__/compiled-truth-revision.test.js.map +1 -1
- package/payload/platform/plugins/memory/mcp/dist/lib/__tests__/phase-backlinks.test.d.ts +2 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/__tests__/phase-backlinks.test.d.ts.map +1 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/__tests__/phase-backlinks.test.js +24 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/__tests__/phase-backlinks.test.js.map +1 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/__tests__/phase-tag-normalisation.test.d.ts +2 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/__tests__/phase-tag-normalisation.test.d.ts.map +1 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/__tests__/phase-tag-normalisation.test.js +51 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/__tests__/phase-tag-normalisation.test.js.map +1 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/compiled-truth-revision.d.ts +31 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/compiled-truth-revision.d.ts.map +1 -1
- package/payload/platform/plugins/memory/mcp/dist/lib/compiled-truth-revision.js.map +1 -1
- package/payload/platform/plugins/memory/mcp/dist/lib/dream-cycle/index.d.ts +7 -7
- package/payload/platform/plugins/memory/mcp/dist/lib/dream-cycle/index.js +7 -7
- package/payload/platform/plugins/memory/mcp/dist/lib/dream-cycle/phase-backlinks.d.ts +15 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/dream-cycle/phase-backlinks.d.ts.map +1 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/dream-cycle/phase-backlinks.js +37 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/dream-cycle/phase-backlinks.js.map +1 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/dream-cycle/phase-tag-normalisation.d.ts +25 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/dream-cycle/phase-tag-normalisation.d.ts.map +1 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/dream-cycle/phase-tag-normalisation.js +90 -0
- package/payload/platform/plugins/memory/mcp/dist/lib/dream-cycle/phase-tag-normalisation.js.map +1 -0
- package/payload/platform/plugins/memory/mcp/dist/tools/__tests__/conversation-archive-derive-insights.test.js +117 -0
- package/payload/platform/plugins/memory/mcp/dist/tools/__tests__/conversation-archive-derive-insights.test.js.map +1 -1
- package/payload/platform/plugins/memory/mcp/dist/tools/__tests__/memory-ingest-inline-rewrite.test.d.ts +2 -0
- package/payload/platform/plugins/memory/mcp/dist/tools/__tests__/memory-ingest-inline-rewrite.test.d.ts.map +1 -0
- package/payload/platform/plugins/memory/mcp/dist/tools/__tests__/memory-ingest-inline-rewrite.test.js +66 -0
- package/payload/platform/plugins/memory/mcp/dist/tools/__tests__/memory-ingest-inline-rewrite.test.js.map +1 -0
- package/payload/platform/plugins/memory/mcp/dist/tools/conversation-archive-derive-insights.d.ts +25 -0
- package/payload/platform/plugins/memory/mcp/dist/tools/conversation-archive-derive-insights.d.ts.map +1 -1
- package/payload/platform/plugins/memory/mcp/dist/tools/conversation-archive-derive-insights.js +26 -0
- package/payload/platform/plugins/memory/mcp/dist/tools/conversation-archive-derive-insights.js.map +1 -1
- package/payload/platform/plugins/memory/mcp/dist/tools/memory-dream-run.d.ts +6 -3
- package/payload/platform/plugins/memory/mcp/dist/tools/memory-dream-run.d.ts.map +1 -1
- package/payload/platform/plugins/memory/mcp/dist/tools/memory-dream-run.js +32 -5
- package/payload/platform/plugins/memory/mcp/dist/tools/memory-dream-run.js.map +1 -1
- package/payload/platform/plugins/memory/mcp/dist/tools/memory-ingest.d.ts +37 -0
- package/payload/platform/plugins/memory/mcp/dist/tools/memory-ingest.d.ts.map +1 -1
- package/payload/platform/plugins/memory/mcp/dist/tools/memory-ingest.js +72 -0
- package/payload/platform/plugins/memory/mcp/dist/tools/memory-ingest.js.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/index.js +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/index.js.map +1 -1
- package/payload/platform/scripts/rss-sampler.sh +58 -0
- package/payload/platform/services/claude-session-manager/dist/http-server.d.ts +4 -0
- package/payload/platform/services/claude-session-manager/dist/http-server.d.ts.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/http-server.js +4 -0
- package/payload/platform/services/claude-session-manager/dist/http-server.js.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/index.js +23 -0
- package/payload/platform/services/claude-session-manager/dist/index.js.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/pty-spawner.d.ts +14 -2
- package/payload/platform/services/claude-session-manager/dist/pty-spawner.d.ts.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/pty-spawner.js +27 -0
- package/payload/platform/services/claude-session-manager/dist/pty-spawner.js.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/rc-daemon.d.ts +6 -0
- package/payload/platform/services/claude-session-manager/dist/rc-daemon.d.ts.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/rc-daemon.js +2 -0
- package/payload/platform/services/claude-session-manager/dist/rc-daemon.js.map +1 -1
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
// Static-grep contracts for Task 600 installer additions:
|
|
2
|
+
// swap provisioning and rss-sampler service registration.
|
|
3
|
+
//
|
|
4
|
+
// Why static-grep, not behaviour: the install branches spawn (sudo, systemctl,
|
|
5
|
+
// dphys-swapfile), so end-to-end reproduction belongs to the manual smoke path.
|
|
6
|
+
// The unit suite pins the branch points so a future refactor that removes them
|
|
7
|
+
// fails loudly here.
|
|
8
|
+
import test from "node:test";
|
|
9
|
+
import assert from "node:assert/strict";
|
|
10
|
+
import { readFileSync } from "node:fs";
|
|
11
|
+
import { fileURLToPath } from "node:url";
|
|
12
|
+
import { dirname, resolve } from "node:path";
|
|
13
|
+
const here = dirname(fileURLToPath(import.meta.url));
|
|
14
|
+
const INDEX_TS = resolve(here, "../../src/index.ts");
|
|
15
|
+
const SRC = readFileSync(INDEX_TS, "utf-8");
|
|
16
|
+
test("installSystemDeps Linux branch installs dphys-swapfile and writes CONF_SWAPSIZE=2048", () => {
|
|
17
|
+
assert.match(SRC, /apt-get.*install.*dphys-swapfile/s, "apt install dphys-swapfile must be present");
|
|
18
|
+
assert.match(SRC, /CONF_SWAPSIZE=2048/, "swap size must be 2048MB");
|
|
19
|
+
assert.match(SRC, /CONF_MAXSWAP=4096/, "swap max must be 4096MB");
|
|
20
|
+
assert.match(SRC, /dphys-swapfile.*restart|restart.*dphys-swapfile/s, "dphys-swapfile service must be restarted");
|
|
21
|
+
});
|
|
22
|
+
test("installService Linux branch writes rss-sampler user unit and enables it", () => {
|
|
23
|
+
assert.match(SRC, /rss-sampler\.service/, "rss-sampler.service unit must be written");
|
|
24
|
+
assert.match(SRC, /rss-sampler\.sh/, "rss-sampler.sh must appear in ExecStart");
|
|
25
|
+
assert.match(SRC, /rss-sampler.*enable|enable.*rss-sampler/s, "rss-sampler must be enabled");
|
|
26
|
+
assert.match(SRC, /rss-sampler installed/, "rss-sampler install must emit a logFile entry");
|
|
27
|
+
});
|
package/dist/index.js
CHANGED
|
@@ -709,6 +709,42 @@ function installSystemDeps() {
|
|
|
709
709
|
// so deployPayload's writeChromiumBinaryPathFile and installService's
|
|
710
710
|
// buildMaxyUnitFile both have a real absolute path to thread through.
|
|
711
711
|
ensureNonSnapChromium();
|
|
712
|
+
// Task 600 — provision swap so the OOM-killer has a buffer to work in
|
|
713
|
+
// instead of silently freezing the box. dphys-swapfile is the standard
|
|
714
|
+
// Raspberry Pi OS swap manager. CONF_MAXSWAP raised to 4096 so the
|
|
715
|
+
// operator can manually grow the swap file without reinstalling.
|
|
716
|
+
// Best-effort: a failure here warns but does not abort the install.
|
|
717
|
+
try {
|
|
718
|
+
console.log(" [privileged] apt-get install dphys-swapfile");
|
|
719
|
+
shell("apt-get", ["install", "-y", "dphys-swapfile"], { sudo: true, bestEffort: true });
|
|
720
|
+
const desiredSwapConf = "CONF_SWAPSIZE=2048\nCONF_MAXSWAP=4096\n";
|
|
721
|
+
const swapConfPath = "/etc/dphys-swapfile";
|
|
722
|
+
let swapCurrent = "";
|
|
723
|
+
if (existsSync(swapConfPath)) {
|
|
724
|
+
try {
|
|
725
|
+
swapCurrent = readFileSync(swapConfPath, "utf-8");
|
|
726
|
+
}
|
|
727
|
+
catch {
|
|
728
|
+
swapCurrent = "";
|
|
729
|
+
}
|
|
730
|
+
}
|
|
731
|
+
if (swapCurrent === desiredSwapConf) {
|
|
732
|
+
logFile(" swap: already configured (CONF_SWAPSIZE=2048 CONF_MAXSWAP=4096)");
|
|
733
|
+
}
|
|
734
|
+
else {
|
|
735
|
+
const swapTmpPath = `/tmp/dphys-swapfile.${process.pid}`;
|
|
736
|
+
writeFileSync(swapTmpPath, desiredSwapConf);
|
|
737
|
+
console.log(" [privileged] install /etc/dphys-swapfile (CONF_SWAPSIZE=2048 CONF_MAXSWAP=4096)");
|
|
738
|
+
shell("cp", [swapTmpPath, swapConfPath], { sudo: true });
|
|
739
|
+
spawnSync("rm", ["-f", swapTmpPath]);
|
|
740
|
+
console.log(" [privileged] systemctl restart dphys-swapfile");
|
|
741
|
+
shell("systemctl", ["restart", "dphys-swapfile"], { sudo: true, bestEffort: true });
|
|
742
|
+
logFile(" swap: configured CONF_SWAPSIZE=2048 CONF_MAXSWAP=4096 and restarted dphys-swapfile");
|
|
743
|
+
}
|
|
744
|
+
}
|
|
745
|
+
catch (err) {
|
|
746
|
+
console.error(` WARNING: failed to provision swap: ${err instanceof Error ? err.message : String(err)}`);
|
|
747
|
+
}
|
|
712
748
|
// Hostname resolution — four sources, in priority order:
|
|
713
749
|
// 1. --hostname flag (unconditional — the caller is the authority)
|
|
714
750
|
// 2. OS detection on same-brand upgrade (service exists → keep whatever is currently set)
|
|
@@ -3084,6 +3120,28 @@ function installService() {
|
|
|
3084
3120
|
const claudePtysSliceName = "claude-ptys.slice";
|
|
3085
3121
|
writeFileSync(join(serviceDir, claudePtysSliceName), buildClaudePtysSliceUnitFile());
|
|
3086
3122
|
logFile(` ${claudePtysSliceName}: Task 250 slice for claude-session-*.scope cohort`);
|
|
3123
|
+
// Task 600 — per-brand RSS sampler: a long-running user service that
|
|
3124
|
+
// periodically writes per-claude.exe RSS + aggregate RSS to disk.
|
|
3125
|
+
// Named per-brand (BRAND.hostname prefix) so two brands on the same
|
|
3126
|
+
// device each own their own sampler writing to their own log path.
|
|
3127
|
+
const rssSamplerUnitName = `${BRAND.hostname}-rss-sampler.service`;
|
|
3128
|
+
const rssSamplerScriptPath = resolve(INSTALL_DIR, "platform/scripts/rss-sampler.sh");
|
|
3129
|
+
const rssSamplerLogPath = join(persistDir, "rss-sampler.log");
|
|
3130
|
+
const rssSamplerUnit = `[Unit]
|
|
3131
|
+
Description=${BRAND.productName} RSS Sampler
|
|
3132
|
+
|
|
3133
|
+
[Service]
|
|
3134
|
+
Type=simple
|
|
3135
|
+
ExecStart=/bin/bash ${rssSamplerScriptPath}
|
|
3136
|
+
Environment=LOG_PATH=${rssSamplerLogPath}
|
|
3137
|
+
Restart=on-failure
|
|
3138
|
+
RestartSec=10
|
|
3139
|
+
|
|
3140
|
+
[Install]
|
|
3141
|
+
WantedBy=default.target
|
|
3142
|
+
`;
|
|
3143
|
+
writeFileSync(join(serviceDir, rssSamplerUnitName), rssSamplerUnit);
|
|
3144
|
+
logFile(` rss-sampler installed: ${rssSamplerUnitName} LOG_PATH=${rssSamplerLogPath}`);
|
|
3087
3145
|
// the edge service: always-on front door that owns the public
|
|
3088
3146
|
// port (PORT) and the VNC stack (Xtigervnc + websockify). Its lifecycle is
|
|
3089
3147
|
// independent of the main brand service, so an in-place upgrade triggered
|
|
@@ -3294,11 +3352,14 @@ WantedBy=multi-user.target
|
|
|
3294
3352
|
spawnSync("systemctl", ["--user", "enable", edgeUnitShort], { stdio: "inherit" });
|
|
3295
3353
|
spawnSync("systemctl", ["--user", "enable", claudeSessionManagerUnitShort], { stdio: "inherit" });
|
|
3296
3354
|
spawnSync("systemctl", ["--user", "enable", unitName], { stdio: "inherit" });
|
|
3355
|
+
spawnSync("systemctl", ["--user", "enable", `${BRAND.hostname}-rss-sampler`], { stdio: "inherit" });
|
|
3297
3356
|
// edge first: binds public port + starts VNC stack. Then claude-session-manager
|
|
3298
3357
|
// (so the main brand unit's Requires= is satisfied). Then main brand service.
|
|
3358
|
+
// rss-sampler is independent — start last, failure is non-blocking.
|
|
3299
3359
|
spawnSync("systemctl", ["--user", "restart", edgeUnitShort], { stdio: "inherit" });
|
|
3300
3360
|
spawnSync("systemctl", ["--user", "restart", claudeSessionManagerUnitShort], { stdio: "inherit" });
|
|
3301
3361
|
spawnSync("systemctl", ["--user", "restart", unitName], { stdio: "inherit" });
|
|
3362
|
+
spawnSync("systemctl", ["--user", "restart", `${BRAND.hostname}-rss-sampler`], { stdio: "inherit" });
|
|
3302
3363
|
// Session manager runs in its own systemd user unit and can boot-fail silently
|
|
3303
3364
|
// (e.g. mcp-block-missing). The web server below comes up regardless, so the
|
|
3304
3365
|
// install terminal would otherwise report success while every API call 503s.
|
package/package.json
CHANGED
|
@@ -205,7 +205,7 @@ Graph hygiene is **agent-directed, case by case** — no autonomous rule engine,
|
|
|
205
205
|
|
|
206
206
|
## Dream-cycle maintenance — `memory-dream-run` / `memory-review-queue`
|
|
207
207
|
|
|
208
|
-
`memory-dream-run` is the operator-initiated graph-hygiene sweep —
|
|
208
|
+
`memory-dream-run` is the operator-initiated graph-hygiene sweep — seven phases: orphan detection on `:Person`/`:Organization`/`:Concept`/`:Project`; stale compiled-truth scan on `compiledTruthUpdatedAt`; mark edges to `:Trashed` targets with `staleTarget: true`; LLM-bounded citation audit on `:TimelineEvent`; prune compiled-truth revisions to newest 20 per entity; materialise persistent `:BACKLINKS` edges derived from `:MENTIONS`/`:REFERENCES` (making reverse-link queries O(1)); normalise `tags[]` array properties on `:KnowledgeDocument` nodes and merge `:DefinedTerm {category:'obsidian-tag'}` variants. Each run writes a `:Report` (via `memory-report-write`) summarising counts; per-phase log lines `[dream-cycle] phase=<n>` join on the run id. Failure of any phase logs `[dream-cycle:phase-<n>:error]` and continues. Pass `phases: [4]` to run only the citation audit (e.g. after a bulk ingest); `maxEventsPerRun` defaults to 200 for phase 4, with a resume cursor stored as `:Report.lastEventCursor`. `memory-review-queue` is the read-only surface for `:OrphanCandidate` and `:CitationProposal` queues — counts plus a small sample per queue. Task 327; absorbs Task 330; extended Task 596.
|
|
209
209
|
|
|
210
210
|
## Brain-capture diagnostic — `memory-brain-capture-recent`
|
|
211
211
|
|
|
@@ -286,3 +286,7 @@ After a successful `memory-ingest` call, the dispatching admin agent should:
|
|
|
286
286
|
3. If the user provides additional keywords post-ingest, call `memory-update` on the `documentNodeId` with the merged array.
|
|
287
287
|
|
|
288
288
|
Keywords support user-defined collections via naming convention (e.g., `["reports", "reports/quarterly", "reports/quarterly/q1-2026"]`).
|
|
289
|
+
|
|
290
|
+
**Inline compiled-truth reconciliation (opt-in).** Pass `inlineRewrite: true` to enable the edge-density gate. After all sections and edges are written, the writer counts MENTIONS and REFERENCES edges from the new document (KnowledgeDocument and its sections) to existing entities that carry `compiledTruth`. Entities with >= `inlineRewriteThreshold` (default 2) such edges qualify — unless their `compiledTruthUpdatedAt` is within the 7-day cooldown, in which case they land in `inlineRewriteDeferred` and remain candidates for the next dream-cycle. The result includes `inlineRewriteCandidates: [{ elementId, label, name, edgeCount }]`. Dispatch the `compiled-truth-rewriter` specialist for each entry before the skill returns; pass `nodeId = entry.elementId` and an optional `operatorHint` if the new source suggests a correction. Pass `forceRewrite: true` to bypass the cooldown. Diagnostic: `grep '[memory-ingest] op=compiled-truth-inline'` shows `entitiesChecked`, `entitiesRecompiled`, `entitiesDeferred`, and `reason` per ingest.
|
|
291
|
+
|
|
292
|
+
For the conversation-archive path, the equivalent signal is in `conversation-archive-derive-insights`: pass `inlineRewrite: true` and optionally `inlineRewriteThreshold` to receive `inlineRewriteSignals` (display name + mention count) in the per-chunk result. The skill accumulates signals across chunks; when a cumulative count hits threshold, resolve the entity via `memory-search` and dispatch the `compiled-truth-rewriter` specialist.
|
|
@@ -504,7 +504,9 @@ server.tool("conversation-archive-derive-insights", "Convert one chunk's agent-p
|
|
|
504
504
|
claims: z
|
|
505
505
|
.array(claimSchema)
|
|
506
506
|
.describe("Claims the dispatched specialist emitted in-turn from the chunk body. Zero is valid — pass [] to record an empty-chunk pass."),
|
|
507
|
-
|
|
507
|
+
inlineRewrite: z.boolean().optional().describe("When true, count mention-claim subjects in this chunk and return those reaching inlineRewriteThreshold in inlineRewriteSignals. The calling skill accumulates signals across chunks; when an entity's cumulative count hits threshold, resolve it via memory-search and dispatch the compiled-truth-rewriter specialist."),
|
|
508
|
+
inlineRewriteThreshold: z.number().int().min(1).optional().describe("Minimum mention-claim count for a subject to appear in inlineRewriteSignals. Default: 2."),
|
|
509
|
+
}, async ({ archiveElementId, chunkElementId, claims, inlineRewrite, inlineRewriteThreshold }) => {
|
|
508
510
|
if (!accountId)
|
|
509
511
|
return refuseNoAccount("conversation-archive-derive-insights");
|
|
510
512
|
try {
|
|
@@ -514,6 +516,8 @@ server.tool("conversation-archive-derive-insights", "Convert one chunk's agent-p
|
|
|
514
516
|
chunkElementId,
|
|
515
517
|
claims: claims,
|
|
516
518
|
sessionId: resolveSessionId(),
|
|
519
|
+
inlineRewrite,
|
|
520
|
+
inlineRewriteThreshold,
|
|
517
521
|
});
|
|
518
522
|
const proposalLines = result.proposals
|
|
519
523
|
.map((p, i) => {
|
|
@@ -532,7 +536,10 @@ server.tool("conversation-archive-derive-insights", "Convert one chunk's agent-p
|
|
|
532
536
|
].join("\n");
|
|
533
537
|
})
|
|
534
538
|
.join("\n\n");
|
|
535
|
-
const
|
|
539
|
+
const signalsSuffix = result.inlineRewriteSignals && result.inlineRewriteSignals.length > 0
|
|
540
|
+
? ` inlineRewriteSignals=${JSON.stringify(result.inlineRewriteSignals)}`
|
|
541
|
+
: "";
|
|
542
|
+
const header = `archiveElementId=${result.archiveElementId} chunkElementId=${result.chunkElementId} proposals=${result.proposals.length} rejectionsFiltered=${result.rejectionsFiltered} invalidClaims=${result.invalidClaims}${signalsSuffix}`;
|
|
536
543
|
return {
|
|
537
544
|
content: [
|
|
538
545
|
{
|
|
@@ -1220,7 +1227,10 @@ if (!readOnly) {
|
|
|
1220
1227
|
documentKeywords: z.array(z.string()).optional().describe("Classifier-extracted topic keywords."),
|
|
1221
1228
|
userKeywords: z.array(z.string()).optional().describe("Keywords explicitly provided by the user. Merged additively with documentKeywords."),
|
|
1222
1229
|
sessionId: z.string().optional().describe("Session UUID for provenance stamping. Optional override; the server falls back to the SESSION_ID env var set by the admin agent at MCP spawn. The agent only needs to pass this when calling outside the normal admin-session context."),
|
|
1223
|
-
|
|
1230
|
+
inlineRewrite: z.boolean().optional().describe("When true, after writing all sections and edges, run the inline compiled-truth reconciliation gate. Counts MENTIONS/REFERENCES edges from this document (KnowledgeDocument + its sections) to existing entities that carry compiledTruth. Entities with >= inlineRewriteThreshold such edges (default 2) and compiledTruthUpdatedAt older than 7 days are returned in inlineRewriteCandidates. Dispatch the compiled-truth-rewriter specialist for each before the skill returns. Disabled by default."),
|
|
1231
|
+
forceRewrite: z.boolean().optional().describe("When inlineRewrite is true, bypass the 7-day per-entity cooldown on compiledTruthUpdatedAt. All threshold-qualifying entities are returned as inlineRewriteCandidates regardless of when their truth was last rewritten."),
|
|
1232
|
+
inlineRewriteThreshold: z.number().int().min(1).optional().describe("Minimum MENTIONS/REFERENCES edge count from this source to an entity for it to qualify as an inline-rewrite candidate. Default: 2."),
|
|
1233
|
+
}, async ({ attachmentId, conversationIdentity, source, archiveSha256, archiveSourceFile, participantElementIds, lastIngestedMessageHash, lastIngestedMessageAt, archiveTitle, cleanupPriorChunks, sessionIndex, documentSummary, anchorNodeId, anchorLabel, sections, documentEdges, orphanCandidates, scope, sourceUrl, sourceType, documentKeywords, userKeywords, sessionId: sessionIdOverride, inlineRewrite, forceRewrite, inlineRewriteThreshold }) => {
|
|
1224
1234
|
if (!accountId)
|
|
1225
1235
|
return refuseNoAccount("memory-ingest");
|
|
1226
1236
|
try {
|
|
@@ -1249,6 +1259,9 @@ if (!readOnly) {
|
|
|
1249
1259
|
documentKeywords,
|
|
1250
1260
|
userKeywords,
|
|
1251
1261
|
sessionId: resolveSessionId(sessionIdOverride),
|
|
1262
|
+
inlineRewrite,
|
|
1263
|
+
forceRewrite,
|
|
1264
|
+
inlineRewriteThreshold,
|
|
1252
1265
|
});
|
|
1253
1266
|
return {
|
|
1254
1267
|
content: [{
|
|
@@ -1264,6 +1277,8 @@ if (!readOnly) {
|
|
|
1264
1277
|
documentSummary: result.documentSummary,
|
|
1265
1278
|
keywords: result.keywords,
|
|
1266
1279
|
cleanedPriorChunks: result.cleanedPriorChunks,
|
|
1280
|
+
inlineRewriteCandidates: result.inlineRewriteCandidates,
|
|
1281
|
+
inlineRewriteDeferred: result.inlineRewriteDeferred,
|
|
1267
1282
|
}),
|
|
1268
1283
|
}],
|
|
1269
1284
|
};
|
|
@@ -2494,13 +2509,14 @@ server.tool("session-retrospective-skip-rate", "Return the ratio of recent sessi
|
|
|
2494
2509
|
// ===================================================================
|
|
2495
2510
|
// Report MCP tools (Task 332) are registered earlier in this file.
|
|
2496
2511
|
// Dream-run calls the same writer in-process for the per-run :Report.
|
|
2497
|
-
server.tool("memory-dream-run", "Operator-initiated dream-cycle: graph-hygiene sweep across
|
|
2512
|
+
server.tool("memory-dream-run", "Operator-initiated dream-cycle: graph-hygiene sweep across seven phases " +
|
|
2498
2513
|
"(orphan detection, stale compiled-truth, edges to :Trashed targets, citation audit on :TimelineEvent, " +
|
|
2499
|
-
"prune compiled-truth revisions
|
|
2514
|
+
"prune compiled-truth revisions, materialise :BACKLINKS edges, tag normalisation). " +
|
|
2500
2515
|
"Writes a :Report node at the end. Failure of any phase logs and continues. " +
|
|
2501
|
-
"Pass phases=[4] to run only the citation audit (e.g. after a bulk ingest),
|
|
2516
|
+
"Pass phases=[4] to run only the citation audit (e.g. after a bulk ingest), phases=[5] for revision prune only, " +
|
|
2517
|
+
"or phases=[6,7] for backlink/tag maintenance only.", {
|
|
2502
2518
|
operatorId: z.string().optional().describe("Identifier of the operator who triggered the run; appears in the report and log line."),
|
|
2503
|
-
phases: z.array(z.number().int().min(1).max(
|
|
2519
|
+
phases: z.array(z.number().int().min(1).max(7)).optional().describe("Subset of phases to run. Default [1,2,3,4,5,6,7]. Order is fixed."),
|
|
2504
2520
|
maxEventsPerRun: z.number().int().positive().optional().describe("Phase 4 cap on :TimelineEvent rows scanned per run. Default 200."),
|
|
2505
2521
|
}, async ({ operatorId, phases, maxEventsPerRun }) => {
|
|
2506
2522
|
if (!accountId)
|