@mrrlin-dev/mcp 0.4.28 → 0.4.32
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/bin.cjs +87 -47
- package/package.json +5 -5
package/dist/bin.cjs
CHANGED
|
@@ -37388,6 +37388,22 @@ function isRunnableProposal(item) {
|
|
|
37388
37388
|
return true;
|
|
37389
37389
|
}
|
|
37390
37390
|
|
|
37391
|
+
// ../../packages/schemas/dist/task-notes.js
|
|
37392
|
+
var TASK_NOTES_BRIEF_SECTIONS = [
|
|
37393
|
+
{ heading: "Context", description: "why this task exists; link to parent/trigger task if follow-up." },
|
|
37394
|
+
{ heading: "Scope", description: "concrete actions and acceptance criteria." },
|
|
37395
|
+
{ heading: "References", description: "links, data, relevant findings (omit if nothing to reference)." }
|
|
37396
|
+
];
|
|
37397
|
+
var TASK_NOTES_JOURNAL_SECTIONS = [
|
|
37398
|
+
{ heading: "Result", description: "what was accomplished, key findings or metrics, follow-up tasks created." },
|
|
37399
|
+
{
|
|
37400
|
+
heading: "Recheck",
|
|
37401
|
+
dated: true,
|
|
37402
|
+
description: "what you checked, what you found, and what happens next."
|
|
37403
|
+
}
|
|
37404
|
+
];
|
|
37405
|
+
var JOURNAL_HEADING_RE = new RegExp(`^##[ \\t]+(${TASK_NOTES_JOURNAL_SECTIONS.map((s) => s.heading).join("|")})\\b[ \\t]*(?:[\u2014\u2013-][ \\t]*(\\S.*?))?[ \\t]*$`);
|
|
37406
|
+
|
|
37391
37407
|
// ../../packages/schemas/dist/index.js
|
|
37392
37408
|
var mrrlinTaskStatusSchema = external_exports.enum([
|
|
37393
37409
|
"backlog",
|
|
@@ -41328,24 +41344,30 @@ function createFailureLog(opts = {}) {
|
|
|
41328
41344
|
const windowMs = opts.windowMs ?? failureLogWindowMs();
|
|
41329
41345
|
const now = opts.now ?? Date.now;
|
|
41330
41346
|
const lastEmit = /* @__PURE__ */ new Map();
|
|
41347
|
+
const KIND_NULL = "\0none";
|
|
41331
41348
|
const counts = /* @__PURE__ */ new Map();
|
|
41332
41349
|
let windowStartedAt = null;
|
|
41333
41350
|
return {
|
|
41334
41351
|
/** Decide whether this failure should be printed. Returns the suppressed count to include in
|
|
41335
41352
|
* the line when it is. */
|
|
41336
41353
|
shouldEmit(operation, kind) {
|
|
41337
|
-
const
|
|
41338
|
-
|
|
41339
|
-
|
|
41340
|
-
|
|
41354
|
+
const kindKey = kind ?? KIND_NULL;
|
|
41355
|
+
let byKind = lastEmit.get(operation);
|
|
41356
|
+
if (!byKind) {
|
|
41357
|
+
byKind = /* @__PURE__ */ new Map();
|
|
41358
|
+
lastEmit.set(operation, byKind);
|
|
41359
|
+
}
|
|
41360
|
+
const prev = byKind.get(kindKey);
|
|
41361
|
+
if (prev != null && now() - prev.at < windowMs) {
|
|
41341
41362
|
prev.suppressed += 1;
|
|
41342
41363
|
return { emit: false, suppressed: prev.suppressed };
|
|
41343
41364
|
}
|
|
41344
|
-
const suppressed =
|
|
41345
|
-
|
|
41365
|
+
const suppressed = prev?.suppressed ?? 0;
|
|
41366
|
+
byKind.set(kindKey, { at: now(), suppressed: 0 });
|
|
41346
41367
|
return { emit: true, suppressed };
|
|
41347
41368
|
},
|
|
41348
|
-
/** A success resets the operation's suppression state, so the next failure
|
|
41369
|
+
/** A success resets the operation's suppression state for EVERY error kind, so the next failure
|
|
41370
|
+
* always prints regardless of which kind it is. */
|
|
41349
41371
|
noteSuccess(operation) {
|
|
41350
41372
|
lastEmit.delete(operation);
|
|
41351
41373
|
},
|
|
@@ -41375,9 +41397,10 @@ function createFailureLog(opts = {}) {
|
|
|
41375
41397
|
}
|
|
41376
41398
|
};
|
|
41377
41399
|
}
|
|
41378
|
-
function failureLogLine(label, error51, suppressed) {
|
|
41400
|
+
function failureLogLine(label, error51, suppressed, note) {
|
|
41401
|
+
const noteText = note ? ` (${note})` : "";
|
|
41379
41402
|
const tail2 = suppressed > 0 ? ` (${suppressed} identical suppressed since the last line)` : "";
|
|
41380
|
-
return `[mrrlin-mcp director-bridge] ${label} failed: ${describeError(error51)}${tail2}
|
|
41403
|
+
return `[mrrlin-mcp director-bridge] ${label} failed${noteText}: ${describeError(error51)}${tail2}
|
|
41381
41404
|
`;
|
|
41382
41405
|
}
|
|
41383
41406
|
|
|
@@ -41397,15 +41420,12 @@ function createTokenRefresher(opts) {
|
|
|
41397
41420
|
opts.failureLog?.noteSuccess("tokenRefresh");
|
|
41398
41421
|
opts.onOk?.();
|
|
41399
41422
|
} catch (error51) {
|
|
41400
|
-
const
|
|
41423
|
+
const line = (suppressed) => failureLogLine("token refresh", error51, suppressed, "will retry next tick");
|
|
41401
41424
|
if (opts.failureLog) {
|
|
41402
41425
|
const { emit, suppressed } = opts.failureLog.shouldEmit("tokenRefresh", errorKind(error51));
|
|
41403
|
-
if (emit) process.stderr.write(
|
|
41426
|
+
if (emit) process.stderr.write(line(suppressed));
|
|
41404
41427
|
} else {
|
|
41405
|
-
process.stderr.write(
|
|
41406
|
-
`[mrrlin-mcp director-bridge] token refresh failed (will retry next tick): ${describeError(error51)}
|
|
41407
|
-
`
|
|
41408
|
-
);
|
|
41428
|
+
process.stderr.write(line(0));
|
|
41409
41429
|
}
|
|
41410
41430
|
opts.onError?.(error51);
|
|
41411
41431
|
}
|
|
@@ -41833,7 +41853,7 @@ Do NOT derail the current task - if the operator has an in-flight question, answ
|
|
|
41833
41853
|
}
|
|
41834
41854
|
|
|
41835
41855
|
// src/_generated/version.ts
|
|
41836
|
-
var PKG_VERSION = "0.4.
|
|
41856
|
+
var PKG_VERSION = "0.4.32";
|
|
41837
41857
|
|
|
41838
41858
|
// src/api-base-url-migrate.ts
|
|
41839
41859
|
var import_node_fs3 = __toESM(require("node:fs"), 1);
|
|
@@ -46035,6 +46055,30 @@ function isDeployGateRunStatus(status) {
|
|
|
46035
46055
|
return status === "dev_deploy" || status === "prod_deploy";
|
|
46036
46056
|
}
|
|
46037
46057
|
|
|
46058
|
+
// src/prompts/task-notes-contract.ts
|
|
46059
|
+
function renderTaskNotesContractLines() {
|
|
46060
|
+
const brief = TASK_NOTES_BRIEF_SECTIONS.map((s) => ` ## ${s.heading} \u2014 ${s.description}`);
|
|
46061
|
+
const [result, recheck] = TASK_NOTES_JOURNAL_SECTIONS;
|
|
46062
|
+
return [
|
|
46063
|
+
"- Notes (markdown): write for a human operator scanning a task list.",
|
|
46064
|
+
" First line: one plain-text sentence summarizing the task (no heading).",
|
|
46065
|
+
" Then scale the structure to complexity:",
|
|
46066
|
+
" For simple tasks \u2014 the one-line summary may be enough. No headings required.",
|
|
46067
|
+
" For non-trivial tasks, use these sections as needed:",
|
|
46068
|
+
...brief,
|
|
46069
|
+
" When closing a task (update_task status=closed_done), APPEND a Result section:",
|
|
46070
|
+
` ## ${result?.heading} \u2014 ${result?.description}`,
|
|
46071
|
+
" When you revisit a task that already has a Result \u2014 a later verification, a retry, a status",
|
|
46072
|
+
" re-check \u2014 APPEND a dated entry instead of rewriting Result:",
|
|
46073
|
+
` ## ${recheck?.heading} \u2014 YYYY-MM-DD \u2014 ${recheck?.description}`,
|
|
46074
|
+
" Do NOT remove earlier sections \u2014 they remain useful for context.",
|
|
46075
|
+
" The sections above the first Result/Recheck are the brief (what the task IS); Result and",
|
|
46076
|
+
" Recheck are the execution journal (what HAPPENED). The task page renders them separately and",
|
|
46077
|
+
" collapses the journal, so keep each kind of content under the right heading.",
|
|
46078
|
+
" Adapt depth to the task: a one-line fix needs one sentence, not four headings."
|
|
46079
|
+
];
|
|
46080
|
+
}
|
|
46081
|
+
|
|
46038
46082
|
// src/turn-deadline.ts
|
|
46039
46083
|
var DEFAULT_TURN_INTERRUPT_TIMEOUT_MS = 5e3;
|
|
46040
46084
|
function withTimeout2(promise2, ms, message) {
|
|
@@ -46608,18 +46652,7 @@ var BASE_INSTRUCTIONS_PREFIX = [
|
|
|
46608
46652
|
"- Title: short, actionable, human-readable. Describe what needs to happen, not internal jargon.",
|
|
46609
46653
|
' Good: "Audit crawled-not-indexed pages and fix 404 errors"',
|
|
46610
46654
|
' Bad: "GSC coverage triage crawled-not-indexed + 404"',
|
|
46611
|
-
|
|
46612
|
-
" First line: one plain-text sentence summarizing the task (no heading).",
|
|
46613
|
-
" Then scale the structure to complexity:",
|
|
46614
|
-
" For simple tasks \u2014 the one-line summary may be enough. No headings required.",
|
|
46615
|
-
" For non-trivial tasks, use these sections as needed:",
|
|
46616
|
-
" ## Context \u2014 why this task exists; link to parent/trigger task if follow-up.",
|
|
46617
|
-
" ## Scope \u2014 concrete actions and acceptance criteria.",
|
|
46618
|
-
" ## References \u2014 links, data, relevant findings (omit if nothing to reference).",
|
|
46619
|
-
" When closing a task (update_task status=closed_done), APPEND a Result section:",
|
|
46620
|
-
" ## Result \u2014 what was accomplished, key findings or metrics, follow-up tasks created.",
|
|
46621
|
-
" Do NOT remove earlier sections \u2014 they remain useful for context.",
|
|
46622
|
-
" Adapt depth to the task: a one-line fix needs one sentence, not four headings.",
|
|
46655
|
+
...renderTaskNotesContractLines(),
|
|
46623
46656
|
"",
|
|
46624
46657
|
// Slice 4 of token-efficient-execution-runs (D8). This is the ONLY way the reasoning behind a
|
|
46625
46658
|
// decision survives past this conversation: a thread is retired once it has accumulated too many
|
|
@@ -48873,12 +48906,14 @@ async function compactChat(input, deps) {
|
|
|
48873
48906
|
);
|
|
48874
48907
|
if (exec.ok) {
|
|
48875
48908
|
const summaryNorm = normalizeWhitespace(exec.text);
|
|
48909
|
+
const hasSomethingToVerify = operatorMessages.length > 0;
|
|
48876
48910
|
const allPresent = operatorMessages.every((op) => {
|
|
48877
48911
|
const opNorm = normalizeWhitespace(op);
|
|
48878
48912
|
return summaryNorm.includes(opNorm);
|
|
48879
48913
|
});
|
|
48914
|
+
const isBlank = exec.text.trim().length === 0;
|
|
48880
48915
|
const withinBudget = Buffer.byteLength(exec.text, "utf8") <= input.budgetBytes;
|
|
48881
|
-
if (allPresent && withinBudget) {
|
|
48916
|
+
if (hasSomethingToVerify && allPresent && !isBlank && withinBudget) {
|
|
48882
48917
|
return { kind: "summary", seed: exec.text };
|
|
48883
48918
|
}
|
|
48884
48919
|
}
|
|
@@ -48902,6 +48937,9 @@ async function compactChat(input, deps) {
|
|
|
48902
48937
|
};
|
|
48903
48938
|
}
|
|
48904
48939
|
const seed = kept.reverse().map(renderMessage).join("\n");
|
|
48940
|
+
if (seed.trim().length === 0) {
|
|
48941
|
+
return { kind: "no-seed", note: "No chat content could be carried forward." };
|
|
48942
|
+
}
|
|
48905
48943
|
return { kind: "raw-tail", seed };
|
|
48906
48944
|
}
|
|
48907
48945
|
|
|
@@ -54209,18 +54247,7 @@ function buildThreadStartParams(msg, config2, desiredModel) {
|
|
|
54209
54247
|
"- Title: short, actionable, human-readable. Describe what needs to happen, not internal jargon.",
|
|
54210
54248
|
' Good: "Audit crawled-not-indexed pages and fix 404 errors"',
|
|
54211
54249
|
' Bad: "GSC coverage triage crawled-not-indexed + 404"',
|
|
54212
|
-
|
|
54213
|
-
" First line: one plain-text sentence summarizing the task (no heading).",
|
|
54214
|
-
" Then scale the structure to complexity:",
|
|
54215
|
-
" For simple tasks \u2014 the one-line summary may be enough. No headings required.",
|
|
54216
|
-
" For non-trivial tasks, use these sections as needed:",
|
|
54217
|
-
" ## Context \u2014 why this task exists; link to parent/trigger task if follow-up.",
|
|
54218
|
-
" ## Scope \u2014 concrete actions and acceptance criteria.",
|
|
54219
|
-
" ## References \u2014 links, data, relevant findings (omit if nothing to reference).",
|
|
54220
|
-
" When closing a task (update_task status=closed_done), APPEND a Result section:",
|
|
54221
|
-
" ## Result \u2014 what was accomplished, key findings or metrics, follow-up tasks created.",
|
|
54222
|
-
" Do NOT remove earlier sections \u2014 they remain useful for context.",
|
|
54223
|
-
" Adapt depth to the task: a one-line fix needs one sentence, not four headings.",
|
|
54250
|
+
...renderTaskNotesContractLines(),
|
|
54224
54251
|
// early-intent-confirmation (design.md, "The chat contract"): the core block below is copied
|
|
54225
54252
|
// VERBATIM from design.md, per tasks.md 10.1. It replaces an older sentence that also carried
|
|
54226
54253
|
// "omit operatorSeedRequest only when there is genuinely no operator request behind the task
|
|
@@ -55182,13 +55209,15 @@ function createBridgeMessageHandler(deps) {
|
|
|
55182
55209
|
provider: compactionSeat.id,
|
|
55183
55210
|
weakModel: compactionSeat.models.weak
|
|
55184
55211
|
});
|
|
55185
|
-
const
|
|
55212
|
+
const rawSeed = result.kind === "no-seed" ? result.note : result.seed;
|
|
55213
|
+
const seed = rawSeed.trim().length > 0 ? rawSeed : "No prior context could be carried forward.";
|
|
55186
55214
|
sendForSpan({
|
|
55187
55215
|
type: "compact-directive",
|
|
55188
55216
|
directorSessionId: directorSessionId2,
|
|
55189
55217
|
lineageId,
|
|
55190
55218
|
resolvedSeat: compactionSeat.id,
|
|
55191
|
-
seed
|
|
55219
|
+
seed,
|
|
55220
|
+
seedKind: result.kind
|
|
55192
55221
|
});
|
|
55193
55222
|
return;
|
|
55194
55223
|
}
|
|
@@ -62626,6 +62655,17 @@ function compactProjectSnapshot(projectSlug, snapshot, maxItems) {
|
|
|
62626
62655
|
}
|
|
62627
62656
|
var ARTIFACT_PAYLOAD_BUDGET = 400;
|
|
62628
62657
|
var COMMAND_OUTPUT_TAIL_LINES = 10;
|
|
62658
|
+
function asString(value) {
|
|
62659
|
+
return typeof value === "string" ? value : null;
|
|
62660
|
+
}
|
|
62661
|
+
function eventContentText(value) {
|
|
62662
|
+
if (typeof value === "string") return value;
|
|
62663
|
+
if (value === null || typeof value !== "object") return null;
|
|
62664
|
+
const blocks = Array.isArray(value) ? value : value.content;
|
|
62665
|
+
if (!Array.isArray(blocks)) return null;
|
|
62666
|
+
const texts = blocks.map((block) => block && typeof block === "object" ? asString(block.text) : null).filter((text) => text !== null);
|
|
62667
|
+
return texts.length > 0 ? texts.join("\n") : null;
|
|
62668
|
+
}
|
|
62629
62669
|
function compactArtifactPayload(artifact) {
|
|
62630
62670
|
const payload = artifact.payload ?? {};
|
|
62631
62671
|
switch (artifact.kind) {
|
|
@@ -62641,10 +62681,10 @@ function compactArtifactPayload(artifact) {
|
|
|
62641
62681
|
}
|
|
62642
62682
|
case "command_output": {
|
|
62643
62683
|
const event = payload.event ?? void 0;
|
|
62644
|
-
const command = payload.command ?? event?.tool?.input?.command ?? null;
|
|
62645
|
-
const cwd = payload.cwd ?? event?.tool?.input?.cwd ?? null;
|
|
62646
|
-
const exitCode = payload.exitCode
|
|
62647
|
-
const rawOutput = payload.stdout ?? payload.output ?? event?.content ?? "";
|
|
62684
|
+
const command = asString(payload.command) ?? asString(event?.tool?.input?.command) ?? null;
|
|
62685
|
+
const cwd = asString(payload.cwd) ?? asString(event?.tool?.input?.cwd) ?? null;
|
|
62686
|
+
const exitCode = typeof payload.exitCode === "number" ? payload.exitCode : null;
|
|
62687
|
+
const rawOutput = eventContentText(payload.stdout) ?? eventContentText(payload.output) ?? eventContentText(event?.content) ?? "";
|
|
62648
62688
|
const lines2 = rawOutput.split(/\r?\n/);
|
|
62649
62689
|
const tail2 = lines2.slice(-COMMAND_OUTPUT_TAIL_LINES).join("\n");
|
|
62650
62690
|
const firstError = lines2.find((l) => /error|fail/i.test(l)) ?? null;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@mrrlin-dev/mcp",
|
|
3
|
-
"version": "0.4.
|
|
3
|
+
"version": "0.4.32",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"bin": {
|
|
6
6
|
"mrrlin-mcp": "dist/bin.cjs"
|
|
@@ -21,12 +21,12 @@
|
|
|
21
21
|
"@types/ws": "^8.18.1",
|
|
22
22
|
"esbuild": "^0.24.0",
|
|
23
23
|
"tsx": "^4.22.3",
|
|
24
|
-
"@mrrlin/agent-client": "0.0.0",
|
|
25
|
-
"@mrrlin/director-e2e": "0.0.0",
|
|
26
24
|
"@mrrlin/client": "0.0.0",
|
|
25
|
+
"@mrrlin/director-e2e": "0.0.0",
|
|
26
|
+
"@mrrlin/schemas": "0.0.0",
|
|
27
27
|
"@mrrlin/tsconfig": "0.0.0",
|
|
28
|
-
"@mrrlin/
|
|
29
|
-
"@mrrlin/
|
|
28
|
+
"@mrrlin/agent-client": "0.0.0",
|
|
29
|
+
"@mrrlin/wiki": "0.0.0"
|
|
30
30
|
},
|
|
31
31
|
"dependencies": {
|
|
32
32
|
"@iarna/toml": "^2.2.5",
|