adhdev 0.9.82-rc.436 → 0.9.82-rc.437
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/cli/adhdev-mcp.js +5 -5
- package/dist/cli/index.js +5 -5
- package/dist/index.js +5 -5
- package/package.json +3 -3
- package/vendor/mcp-server/index.js +100 -5
- package/vendor/mcp-server/index.js.map +1 -1
package/dist/cli/adhdev-mcp.js
CHANGED
|
@@ -1293,10 +1293,10 @@ function readInjected(value) {
|
|
|
1293
1293
|
}
|
|
1294
1294
|
function getDaemonBuildInfo() {
|
|
1295
1295
|
if (cached) return cached;
|
|
1296
|
-
const commit = readInjected(true ? "
|
|
1297
|
-
const commitShort = readInjected(true ? "
|
|
1298
|
-
const version2 = readInjected(true ? "0.9.82-rc.
|
|
1299
|
-
const builtAt = readInjected(true ? "2026-
|
|
1296
|
+
const commit = readInjected(true ? "07c5209009300611151cd8363b63b4b066b6ecec" : void 0) ?? "unknown";
|
|
1297
|
+
const commitShort = readInjected(true ? "07c52090" : void 0) ?? (commit !== "unknown" ? commit.slice(0, 7) : "unknown");
|
|
1298
|
+
const version2 = readInjected(true ? "0.9.82-rc.437" : void 0) ?? readInjected(typeof process !== "undefined" ? "0.9.82-rc.437" : void 0) ?? "unknown";
|
|
1299
|
+
const builtAt = readInjected(true ? "2026-07-01T00:49:56.746Z" : void 0);
|
|
1300
1300
|
cached = builtAt ? { commit, commitShort, version: version2, builtAt } : { commit, commitShort, version: version2 };
|
|
1301
1301
|
return cached;
|
|
1302
1302
|
}
|
|
@@ -137520,7 +137520,7 @@ var init_adhdev_daemon = __esm({
|
|
|
137520
137520
|
init_version();
|
|
137521
137521
|
init_src();
|
|
137522
137522
|
init_runtime_defaults();
|
|
137523
|
-
pkgVersion = resolvePackageVersion({ injectedVersion: "0.9.82-rc.
|
|
137523
|
+
pkgVersion = resolvePackageVersion({ injectedVersion: "0.9.82-rc.437" });
|
|
137524
137524
|
LOCAL_DAEMON_HEALTH_TIMEOUT_MS = 8e3;
|
|
137525
137525
|
AdhdevDaemon = class _AdhdevDaemon {
|
|
137526
137526
|
localHttpServer = null;
|
package/dist/cli/index.js
CHANGED
|
@@ -1293,10 +1293,10 @@ function readInjected(value) {
|
|
|
1293
1293
|
}
|
|
1294
1294
|
function getDaemonBuildInfo() {
|
|
1295
1295
|
if (cached) return cached;
|
|
1296
|
-
const commit = readInjected(true ? "
|
|
1297
|
-
const commitShort = readInjected(true ? "
|
|
1298
|
-
const version2 = readInjected(true ? "0.9.82-rc.
|
|
1299
|
-
const builtAt = readInjected(true ? "2026-
|
|
1296
|
+
const commit = readInjected(true ? "07c5209009300611151cd8363b63b4b066b6ecec" : void 0) ?? "unknown";
|
|
1297
|
+
const commitShort = readInjected(true ? "07c52090" : void 0) ?? (commit !== "unknown" ? commit.slice(0, 7) : "unknown");
|
|
1298
|
+
const version2 = readInjected(true ? "0.9.82-rc.437" : void 0) ?? readInjected(typeof process !== "undefined" ? "0.9.82-rc.437" : void 0) ?? "unknown";
|
|
1299
|
+
const builtAt = readInjected(true ? "2026-07-01T00:49:56.746Z" : void 0);
|
|
1300
1300
|
cached = builtAt ? { commit, commitShort, version: version2, builtAt } : { commit, commitShort, version: version2 };
|
|
1301
1301
|
return cached;
|
|
1302
1302
|
}
|
|
@@ -137490,7 +137490,7 @@ var init_adhdev_daemon = __esm({
|
|
|
137490
137490
|
init_version();
|
|
137491
137491
|
init_src();
|
|
137492
137492
|
init_runtime_defaults();
|
|
137493
|
-
pkgVersion = resolvePackageVersion({ injectedVersion: "0.9.82-rc.
|
|
137493
|
+
pkgVersion = resolvePackageVersion({ injectedVersion: "0.9.82-rc.437" });
|
|
137494
137494
|
LOCAL_DAEMON_HEALTH_TIMEOUT_MS = 8e3;
|
|
137495
137495
|
AdhdevDaemon = class _AdhdevDaemon {
|
|
137496
137496
|
localHttpServer = null;
|
package/dist/index.js
CHANGED
|
@@ -773,10 +773,10 @@ function readInjected(value) {
|
|
|
773
773
|
}
|
|
774
774
|
function getDaemonBuildInfo() {
|
|
775
775
|
if (cached) return cached;
|
|
776
|
-
const commit = readInjected(true ? "
|
|
777
|
-
const commitShort = readInjected(true ? "
|
|
778
|
-
const version2 = readInjected(true ? "0.9.82-rc.
|
|
779
|
-
const builtAt = readInjected(true ? "2026-
|
|
776
|
+
const commit = readInjected(true ? "07c5209009300611151cd8363b63b4b066b6ecec" : void 0) ?? "unknown";
|
|
777
|
+
const commitShort = readInjected(true ? "07c52090" : void 0) ?? (commit !== "unknown" ? commit.slice(0, 7) : "unknown");
|
|
778
|
+
const version2 = readInjected(true ? "0.9.82-rc.437" : void 0) ?? readInjected(typeof process !== "undefined" ? "0.9.82-rc.437" : void 0) ?? "unknown";
|
|
779
|
+
const builtAt = readInjected(true ? "2026-07-01T00:49:56.746Z" : void 0);
|
|
780
780
|
cached = builtAt ? { commit, commitShort, version: version2, builtAt } : { commit, commitShort, version: version2 };
|
|
781
781
|
return cached;
|
|
782
782
|
}
|
|
@@ -106312,7 +106312,7 @@ var init_adhdev_daemon = __esm({
|
|
|
106312
106312
|
init_version();
|
|
106313
106313
|
init_src();
|
|
106314
106314
|
init_runtime_defaults();
|
|
106315
|
-
pkgVersion = resolvePackageVersion({ injectedVersion: "0.9.82-rc.
|
|
106315
|
+
pkgVersion = resolvePackageVersion({ injectedVersion: "0.9.82-rc.437" });
|
|
106316
106316
|
LOCAL_DAEMON_HEALTH_TIMEOUT_MS = 8e3;
|
|
106317
106317
|
AdhdevDaemon = class _AdhdevDaemon {
|
|
106318
106318
|
localHttpServer = null;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "adhdev",
|
|
3
|
-
"version": "0.9.82-rc.
|
|
3
|
+
"version": "0.9.82-rc.437",
|
|
4
4
|
"description": "ADHDev — Agent Dashboard Hub for Dev. The control hub for your AI coding agents (Claude Code, Codex, Hermes, …).",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"bin": {
|
|
@@ -49,9 +49,9 @@
|
|
|
49
49
|
"node": ">=18"
|
|
50
50
|
},
|
|
51
51
|
"dependencies": {
|
|
52
|
-
"@adhdev/daemon-core": "0.9.82-rc.
|
|
52
|
+
"@adhdev/daemon-core": "0.9.82-rc.437",
|
|
53
53
|
"@adhdev/ghostty-vt-node": "*",
|
|
54
|
-
"@adhdev/mesh-shared": "0.9.82-rc.
|
|
54
|
+
"@adhdev/mesh-shared": "0.9.82-rc.437",
|
|
55
55
|
"@modelcontextprotocol/sdk": "^1.0.0",
|
|
56
56
|
"@xterm/addon-serialize": "^0.14.0",
|
|
57
57
|
"@xterm/xterm": "^6.0.0",
|
|
@@ -1150,14 +1150,14 @@ var MESH_REVIEW_INBOX_TOOL = {
|
|
|
1150
1150
|
};
|
|
1151
1151
|
var MESH_MAGI_REVIEW_TOOL = {
|
|
1152
1152
|
name: "mesh_magi_review",
|
|
1153
|
-
description:
|
|
1153
|
+
description: "Cross-verify a read-only investigation across a standing panel of independent mesh agents (different machines/providers), instead of sending a SINGLE read-only worker. Drop-in for any read-only investigation \u2014 bug RCA, defect/regression measurement, \"why does this code do X?\", or doc/design/API review. Fans the SAME question out to N independent (node \xD7 provider) replicas, then synthesizes consensus/disagreement/unique evidence into a needs_verification list \u2014 NOT a majority vote (high agreement among coupled agents \u2260 correct). Read-only is FORCED (no execute/write flag exists). COST: multiplies token spend by the total replica count (the call is the opt-in). NO pre-authored panel is required: omit `panel` and `members` and pass only `task_kind` (plus the question) to auto-synthesize a maximally-diverse cross-provider PRESET panel from the LIVE mesh \u2014 the resolver enumerates every routable (node \xD7 provider) pair (seeing a node's 2nd+ priority providers, matching the queue's per-provider claim check) and greedily picks the most independent set for that kind. Still resolves to \u22652 (node, provider) targets; never silently degrades to N=1 (errors magi_insufficient_providers if the live mesh cannot supply them).",
|
|
1154
1154
|
inputSchema: {
|
|
1155
1155
|
type: "object",
|
|
1156
1156
|
properties: {
|
|
1157
1157
|
question: { type: "string", description: 'The single investigation question every agent answers \u2014 e.g. "What is the root cause of this defect?", "Refute this RCA.", "Why does this code do X?". Not only "review this".' },
|
|
1158
1158
|
target: { type: "string", description: "What to investigate \u2014 file path(s), a bug symptom / error / stack trace, a code area / symbol, or omitted when the question is self-contained." },
|
|
1159
1159
|
artifacts: { type: "array", items: { type: "string" }, description: "Inline content when not file-backed: a doc/diff, a log/error dump, or a prior single-worker RCA to refute." },
|
|
1160
|
-
panel: { type: "string", description: 'Named panel from meshes.json (mesh_magi_panel_set).
|
|
1160
|
+
panel: { type: "string", description: 'Named panel from meshes.json (mesh_magi_panel_set). When omitted: if task_kind is given (and no inline members), a maximally-diverse cross-provider preset panel is auto-synthesized from the live mesh; otherwise falls back to a panel named "default" and errors clearly if none exists. Ignored when inline members are provided.' },
|
|
1161
1161
|
members: {
|
|
1162
1162
|
type: "array",
|
|
1163
1163
|
description: "Inline ad-hoc panel override (NOT persisted): same member shape as a configured panel. When present, the named panel is ignored. Maximize distinct providers AND machines for real independence.",
|
|
@@ -1173,7 +1173,7 @@ var MESH_MAGI_REVIEW_TOOL = {
|
|
|
1173
1173
|
}
|
|
1174
1174
|
},
|
|
1175
1175
|
n: { type: "number", description: "Global replica override per member (clamped by the total-replica guard cap, default 12)." },
|
|
1176
|
-
task_kind: { type: "string", enum: ["claim_audit", "rca", "design", "freeform"], description: "Selects the SINGLE output schema injected into each replica prompt and the strict parser used at collection (no schema-on-schema conflict). claim_audit (DEFAULT, backward-compatible): {claims[],top_findings[],open_questions[]}. rca: {rootCause,failsAt,mechanism,evidence[],fixDirection,confidence}. design: {recommendation,rationale,alternatives[],tradeoffs[],risks[],evidence[],confidence}. freeform: no schema \u2014 natural-language answer, parsing/evidence checks waived, cross-verification is weak. Every kind except freeform requires non-empty evidence[]; an empty-evidence or schema-invalid answer triggers ONE delta re-request before being dropped as unparseable. Do NOT also embed an output-format schema in the question \u2014 it collides with this contract (a warning is surfaced if detected)." },
|
|
1176
|
+
task_kind: { type: "string", enum: ["claim_audit", "rca", "design", "freeform"], description: "Selects the SINGLE output schema injected into each replica prompt and the strict parser used at collection (no schema-on-schema conflict). claim_audit (DEFAULT, backward-compatible): {claims[],top_findings[],open_questions[]}. rca: {rootCause,failsAt,mechanism,evidence[],fixDirection,confidence}. design: {recommendation,rationale,alternatives[],tradeoffs[],risks[],evidence[],confidence}. freeform: no schema \u2014 natural-language answer, parsing/evidence checks waived, cross-verification is weak. When `panel` and `members` are both omitted, task_kind ALSO drives auto-synthesis of a maximally-diverse cross-provider preset panel from the live mesh (design fans out widest, claim_audit/rca a triad, freeform the minimum pair). Every kind except freeform requires non-empty evidence[]; an empty-evidence or schema-invalid answer triggers ONE delta re-request before being dropped as unparseable. Do NOT also embed an output-format schema in the question \u2014 it collides with this contract (a warning is surfaced if detected)." },
|
|
1177
1177
|
mode: { type: "string", enum: ["rca", "investigation", "claim_audit", "design_review", "code_audit"], description: "Synthesis emphasis hint \u2014 affects labels only, never the agent count or schema. Distinct from task_kind (which selects the output schema)." },
|
|
1178
1178
|
use_judge: { type: "boolean", description: "Default false (clustering synthesis). STUB: judge synthesis is not yet implemented \u2014 passing true currently falls back to clustering with a warning. Reserved interface only." },
|
|
1179
1179
|
require_independent_evidence: { type: "boolean", description: "Default true \u2014 high-impact claims with no file:line/source evidence are routed to needs_verification." },
|
|
@@ -4089,6 +4089,12 @@ var MAGI_MAX_WAIT_MS = 6e5;
|
|
|
4089
4089
|
var MAGI_POLL_INTERVAL_MS = 5e3;
|
|
4090
4090
|
var VALID_TASK_KINDS = ["claim_audit", "rca", "design", "freeform"];
|
|
4091
4091
|
var DEFAULT_TASK_KIND = "claim_audit";
|
|
4092
|
+
var MAGI_KIND_PRESETS = {
|
|
4093
|
+
claim_audit: { targetK: 3, minK: 2, providerPreference: ["claude-cli", "codex-cli", "gemini-cli", "hermes-cli"], avoidConcurrentProviders: ["antigravity-cli"] },
|
|
4094
|
+
rca: { targetK: 3, minK: 2, providerPreference: ["claude-cli", "codex-cli", "gemini-cli", "hermes-cli"], avoidConcurrentProviders: ["antigravity-cli"] },
|
|
4095
|
+
design: { targetK: 4, minK: 2, providerPreference: ["claude-cli", "codex-cli", "gemini-cli", "hermes-cli"], avoidConcurrentProviders: ["antigravity-cli"] },
|
|
4096
|
+
freeform: { targetK: 2, minK: 2, providerPreference: ["claude-cli", "codex-cli", "gemini-cli", "hermes-cli"], avoidConcurrentProviders: ["antigravity-cli"] }
|
|
4097
|
+
};
|
|
4092
4098
|
function normalizeMagiTaskKind(raw) {
|
|
4093
4099
|
const s = typeof raw === "string" ? raw.trim().toLowerCase() : "";
|
|
4094
4100
|
return VALID_TASK_KINDS.includes(s) ? s : DEFAULT_TASK_KIND;
|
|
@@ -4811,6 +4817,77 @@ function buildInlineMagiPanel(members, opts = {}) {
|
|
|
4811
4817
|
description: opts.description ?? "inline ad-hoc panel"
|
|
4812
4818
|
});
|
|
4813
4819
|
}
|
|
4820
|
+
function enumerateLivePresetCandidates(nodes) {
|
|
4821
|
+
const out = [];
|
|
4822
|
+
const seen = /* @__PURE__ */ new Set();
|
|
4823
|
+
for (const node of Array.isArray(nodes) ? nodes : []) {
|
|
4824
|
+
const nodeId = node?.id;
|
|
4825
|
+
if (typeof nodeId !== "string" || !nodeId.trim()) continue;
|
|
4826
|
+
for (const provider of readProviderPriority(node?.policy)) {
|
|
4827
|
+
const tags = (0, import_daemon_core4.buildMeshNodeCapabilityTags)(node, provider);
|
|
4828
|
+
if (!(0, import_daemon_core4.nodeSatisfiesRequiredTags)([`provider=${provider}`], tags)) continue;
|
|
4829
|
+
const key = `${nodeId}|${provider}`;
|
|
4830
|
+
if (seen.has(key)) continue;
|
|
4831
|
+
seen.add(key);
|
|
4832
|
+
out.push({ nodeId, provider });
|
|
4833
|
+
}
|
|
4834
|
+
}
|
|
4835
|
+
return out;
|
|
4836
|
+
}
|
|
4837
|
+
function selectDiversePresetPairs(candidates, preset) {
|
|
4838
|
+
const prefRank = /* @__PURE__ */ new Map();
|
|
4839
|
+
(preset.providerPreference ?? []).forEach((p, i) => prefRank.set(p, i));
|
|
4840
|
+
const prefOf = (provider) => prefRank.has(provider) ? prefRank.get(provider) : Number.MAX_SAFE_INTEGER;
|
|
4841
|
+
const fragile = new Set(preset.avoidConcurrentProviders ?? []);
|
|
4842
|
+
const scarcity = /* @__PURE__ */ new Map();
|
|
4843
|
+
for (const c of candidates) scarcity.set(c.provider, (scarcity.get(c.provider) ?? 0) + 1);
|
|
4844
|
+
const sorted = [...candidates].sort(
|
|
4845
|
+
(a, b) => prefOf(a.provider) - prefOf(b.provider) || (scarcity.get(a.provider) ?? 0) - (scarcity.get(b.provider) ?? 0) || (a.nodeId < b.nodeId ? -1 : a.nodeId > b.nodeId ? 1 : 0) || (a.provider < b.provider ? -1 : a.provider > b.provider ? 1 : 0)
|
|
4846
|
+
);
|
|
4847
|
+
const picked = [];
|
|
4848
|
+
const usedNodes = /* @__PURE__ */ new Set();
|
|
4849
|
+
const usedProviders = /* @__PURE__ */ new Set();
|
|
4850
|
+
const fragileNodes = /* @__PURE__ */ new Set();
|
|
4851
|
+
const tryPick = (c) => {
|
|
4852
|
+
if (picked.length >= preset.targetK) return;
|
|
4853
|
+
if (fragile.has(c.provider) && fragileNodes.has(c.nodeId)) return;
|
|
4854
|
+
picked.push(c);
|
|
4855
|
+
usedNodes.add(c.nodeId);
|
|
4856
|
+
usedProviders.add(c.provider);
|
|
4857
|
+
if (fragile.has(c.provider)) fragileNodes.add(c.nodeId);
|
|
4858
|
+
};
|
|
4859
|
+
const isPicked = (c) => picked.some((p) => p.nodeId === c.nodeId && p.provider === c.provider);
|
|
4860
|
+
for (const c of sorted) {
|
|
4861
|
+
if (picked.length >= preset.targetK) break;
|
|
4862
|
+
if (isPicked(c)) continue;
|
|
4863
|
+
if (!usedProviders.has(c.provider) && !usedNodes.has(c.nodeId)) tryPick(c);
|
|
4864
|
+
}
|
|
4865
|
+
for (const c of sorted) {
|
|
4866
|
+
if (picked.length >= preset.targetK) break;
|
|
4867
|
+
if (isPicked(c)) continue;
|
|
4868
|
+
if (!usedProviders.has(c.provider) || !usedNodes.has(c.nodeId)) tryPick(c);
|
|
4869
|
+
}
|
|
4870
|
+
for (const c of sorted) {
|
|
4871
|
+
if (picked.length >= preset.targetK) break;
|
|
4872
|
+
if (isPicked(c)) continue;
|
|
4873
|
+
tryPick(c);
|
|
4874
|
+
}
|
|
4875
|
+
return picked;
|
|
4876
|
+
}
|
|
4877
|
+
function buildPresetMagiPanelForKind(kind, nodes, opts = {}) {
|
|
4878
|
+
const preset = MAGI_KIND_PRESETS[kind] ?? MAGI_KIND_PRESETS[DEFAULT_TASK_KIND];
|
|
4879
|
+
const candidates = enumerateLivePresetCandidates(nodes);
|
|
4880
|
+
const pairs = selectDiversePresetPairs(candidates, preset);
|
|
4881
|
+
const members = pairs.map((p) => ({
|
|
4882
|
+
provider: p.provider,
|
|
4883
|
+
nodeId: p.nodeId,
|
|
4884
|
+
...opts.n !== void 0 ? { n: Math.max(1, Math.floor(opts.n)) } : { n: 1 }
|
|
4885
|
+
}));
|
|
4886
|
+
if (members.length === 0) {
|
|
4887
|
+
return { members: [], description: `preset:${kind}` };
|
|
4888
|
+
}
|
|
4889
|
+
return buildInlineMagiPanel(members, { defaultN: opts.n, description: `preset:${kind}` });
|
|
4890
|
+
}
|
|
4814
4891
|
async function meshMagiPanelList(ctx, args = {}) {
|
|
4815
4892
|
await refreshMeshFromDaemon(ctx);
|
|
4816
4893
|
const all = (0, import_daemon_core4.listMagiPanels)();
|
|
@@ -4862,9 +4939,13 @@ async function meshMagiReview(ctx, args) {
|
|
|
4862
4939
|
const useJudge = (args.use_judge ?? args.useJudge) === true;
|
|
4863
4940
|
const judgeWarning = useJudge ? "use_judge=true requested, but judge synthesis is not yet implemented \u2014 falling back to clustering synthesis." : null;
|
|
4864
4941
|
await refreshMeshFromDaemon(ctx);
|
|
4942
|
+
const referenceCommit = resolveMagiReferenceCommit(ctx);
|
|
4865
4943
|
const hasInlineMembers = Array.isArray(args.members) && args.members.length > 0;
|
|
4944
|
+
const explicitPanelName = readString(args.panel);
|
|
4945
|
+
const usePresetPath = !hasInlineMembers && !explicitPanelName && typeof explicitTaskKind === "string" && VALID_TASK_KINDS.includes(explicitTaskKind.trim().toLowerCase());
|
|
4866
4946
|
let panel;
|
|
4867
4947
|
let panelName;
|
|
4948
|
+
let presetKind;
|
|
4868
4949
|
if (hasInlineMembers) {
|
|
4869
4950
|
panelName = "(inline)";
|
|
4870
4951
|
try {
|
|
@@ -4877,8 +4958,23 @@ async function meshMagiReview(ctx, args) {
|
|
|
4877
4958
|
hint: "Inline members use the same shape as a configured panel: [{ provider (REQUIRED), nodeId?, capabilityTags?, n? }]."
|
|
4878
4959
|
});
|
|
4879
4960
|
}
|
|
4961
|
+
} else if (usePresetPath) {
|
|
4962
|
+
presetKind = normalizeMagiTaskKind(explicitTaskKind);
|
|
4963
|
+
panelName = `(preset:${presetKind})`;
|
|
4964
|
+
const preset = MAGI_KIND_PRESETS[presetKind];
|
|
4965
|
+
const maxReplicas = Math.max(1, Math.floor(Number(args.n) > 0 ? Number(args.n) : MAGI_MAX_REPLICAS));
|
|
4966
|
+
panel = buildPresetMagiPanelForKind(presetKind, ctx.mesh.nodes, { n: args.n, referenceCommit, maxReplicas });
|
|
4967
|
+
if (panel.members.length < preset.minK) {
|
|
4968
|
+
return JSON.stringify({
|
|
4969
|
+
success: false,
|
|
4970
|
+
code: "magi_insufficient_providers",
|
|
4971
|
+
error: `task_kind '${presetKind}' auto-synthesis found only ${panel.members.length} independent (node, provider) target(s) in the live mesh; MAGI requires \u2265${preset.minK} and never silently degrades to N=1.`,
|
|
4972
|
+
resolvedMembers: panel.members,
|
|
4973
|
+
hint: "Bring a second provider or a second node online (mesh_status to inspect), or pass explicit inline members to mesh_magi_review."
|
|
4974
|
+
}, null, 2);
|
|
4975
|
+
}
|
|
4880
4976
|
} else {
|
|
4881
|
-
panelName =
|
|
4977
|
+
panelName = explicitPanelName || "default";
|
|
4882
4978
|
panel = (0, import_daemon_core4.getMagiPanel)(panelName);
|
|
4883
4979
|
}
|
|
4884
4980
|
if (!panel) {
|
|
@@ -4891,7 +4987,6 @@ async function meshMagiReview(ctx, args) {
|
|
|
4891
4987
|
}
|
|
4892
4988
|
const taskKind = normalizeMagiTaskKind(explicitTaskKind ?? panel.defaultKind);
|
|
4893
4989
|
const includeStale = (args.include_stale ?? args.includeStale) === true;
|
|
4894
|
-
const referenceCommit = resolveMagiReferenceCommit(ctx);
|
|
4895
4990
|
const plan = buildMagiFanoutPlan(panel, ctx.mesh.nodes, { n: args.n, referenceCommit, includeStale });
|
|
4896
4991
|
if (!plan.enoughTargets) {
|
|
4897
4992
|
const droppedByStale = plan.staleMembers.length > 0;
|