@dadado/agent-kit-cli 5.6.0 → 5.8.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 +9 -5
- package/dashboard/README.md +17 -0
- package/dashboard/dashboard-data.mjs +215 -5
- package/dashboard/dashboard.html +285 -1
- package/dashboard/lib/live-refresh.d.mts +23 -0
- package/dashboard/lib/semantic-model.mjs +12 -5
- package/dist/index.js +3052 -1209
- package/package.json +1 -1
package/dashboard/dashboard.html
CHANGED
|
@@ -1173,6 +1173,45 @@ body.mc-fullscreen .top-tabs-row {
|
|
|
1173
1173
|
color: var(--text-secondary);
|
|
1174
1174
|
margin: 12px 0 6px;
|
|
1175
1175
|
}
|
|
1176
|
+
.git-graph-title:first-child { margin-top: 0; }
|
|
1177
|
+
|
|
1178
|
+
/* ===== DevOps ===== */
|
|
1179
|
+
/* Row visual language mirrors .git-flow-row (state dot + lane + meta) so the
|
|
1180
|
+
* new tab reads as the same product, not a second component vocabulary. */
|
|
1181
|
+
.devops-row {
|
|
1182
|
+
display: flex;
|
|
1183
|
+
align-items: center;
|
|
1184
|
+
gap: 10px;
|
|
1185
|
+
font-size: 12px;
|
|
1186
|
+
padding: 8px 10px;
|
|
1187
|
+
border: 1px solid var(--border);
|
|
1188
|
+
border-radius: 8px;
|
|
1189
|
+
background: var(--bg-card);
|
|
1190
|
+
flex-wrap: wrap;
|
|
1191
|
+
margin-bottom: 6px;
|
|
1192
|
+
}
|
|
1193
|
+
.devops-row:last-child { margin-bottom: 0; }
|
|
1194
|
+
.devops-name {
|
|
1195
|
+
font-weight: 600;
|
|
1196
|
+
color: var(--text-primary);
|
|
1197
|
+
flex-shrink: 0;
|
|
1198
|
+
}
|
|
1199
|
+
.devops-meta {
|
|
1200
|
+
color: var(--text-secondary);
|
|
1201
|
+
flex: 1;
|
|
1202
|
+
min-width: 0;
|
|
1203
|
+
}
|
|
1204
|
+
.devops-time {
|
|
1205
|
+
color: var(--text-muted);
|
|
1206
|
+
font-family: var(--mc-font-mono);
|
|
1207
|
+
font-size: 11px;
|
|
1208
|
+
flex-shrink: 0;
|
|
1209
|
+
}
|
|
1210
|
+
.devops-note {
|
|
1211
|
+
font-size: 11px;
|
|
1212
|
+
color: var(--text-muted);
|
|
1213
|
+
margin: 0 0 8px;
|
|
1214
|
+
}
|
|
1176
1215
|
.git-hygiene {
|
|
1177
1216
|
display: flex;
|
|
1178
1217
|
align-items: flex-start;
|
|
@@ -3644,6 +3683,10 @@ html[data-monitor-density="comfortable"] .live-activity-feed .monitor-row .monit
|
|
|
3644
3683
|
Git
|
|
3645
3684
|
<span class="dot dot-gray" id="navGitDot" aria-hidden="true"></span>
|
|
3646
3685
|
</a>
|
|
3686
|
+
<a class="top-tab nav-more-item" role="menuitem" href="#" data-section="devops" tabindex="0" onclick="return showSection('devops')" aria-label="DevOps section">
|
|
3687
|
+
DevOps
|
|
3688
|
+
<span class="dot dot-gray" id="navDevopsDot" aria-hidden="true"></span>
|
|
3689
|
+
</a>
|
|
3647
3690
|
<a class="top-tab nav-more-item" role="menuitem" href="#" data-section="memory" tabindex="0" onclick="return showSection('memory')" aria-label="Memory section">
|
|
3648
3691
|
Memory
|
|
3649
3692
|
</a>
|
|
@@ -3819,6 +3862,7 @@ const SECTION_IDS = [
|
|
|
3819
3862
|
'commands',
|
|
3820
3863
|
'health',
|
|
3821
3864
|
'git',
|
|
3865
|
+
'devops',
|
|
3822
3866
|
'memory',
|
|
3823
3867
|
'terminals',
|
|
3824
3868
|
'processes',
|
|
@@ -5430,6 +5474,199 @@ function renderGitGraphCard(git) {
|
|
|
5430
5474
|
`;
|
|
5431
5475
|
}
|
|
5432
5476
|
|
|
5477
|
+
/** Cap for the visual tree row count (mirrors MAX_GIT_GRAPH_LINES server-side cap, further
|
|
5478
|
+
* bounded here so the stepper stays a glance, not a scroll well). */
|
|
5479
|
+
const MAX_GIT_VISUAL_TREE_ROWS = 12;
|
|
5480
|
+
|
|
5481
|
+
/**
|
|
5482
|
+
* Parse `git log --graph --oneline --decorate` lines into flattened commit
|
|
5483
|
+
* entries. Connector-only lines (`|`, `/`, `\`, whitespace between lanes)
|
|
5484
|
+
* carry no commit and are skipped — see the plan's "Phase 0 lane-flattening
|
|
5485
|
+
* interpretation" note: this trades true branch-lane geometry (still fully
|
|
5486
|
+
* present in the kept markdown block) for one row per commit.
|
|
5487
|
+
*/
|
|
5488
|
+
function parseGitGraphCommits(lines) {
|
|
5489
|
+
const commits = [];
|
|
5490
|
+
for (const line of Array.isArray(lines) ? lines : []) {
|
|
5491
|
+
const m = /\*\s*([0-9a-f]{4,40})\s+(?:\(([^)]*)\)\s*)?(.*)$/.exec(line);
|
|
5492
|
+
if (!m) continue;
|
|
5493
|
+
const decoration = (m[2] || '').trim();
|
|
5494
|
+
commits.push({
|
|
5495
|
+
hash: m[1],
|
|
5496
|
+
decoration,
|
|
5497
|
+
subject: (m[3] || '').trim(),
|
|
5498
|
+
isHead: /\bHEAD\b/.test(decoration),
|
|
5499
|
+
isPromoted: /\borigin\/(main|staging)\b/.test(decoration),
|
|
5500
|
+
});
|
|
5501
|
+
}
|
|
5502
|
+
return commits;
|
|
5503
|
+
}
|
|
5504
|
+
|
|
5505
|
+
/**
|
|
5506
|
+
* Visual companion to the markdown git-graph block: reuses the exact
|
|
5507
|
+
* .now-stepper/.now-step/.now-step-marker timeline primitive (state-colored
|
|
5508
|
+
* markers + connecting line) with one row per parsed commit. Dot/marker
|
|
5509
|
+
* semantics stay locked to the existing Now-panel vocabulary: current/blue =
|
|
5510
|
+
* HEAD, done/green = already promoted to origin/main or origin/staging,
|
|
5511
|
+
* neutral = neither. Degrades to a compact empty-state when the graph has no
|
|
5512
|
+
* parseable commit line (e.g. a shallow clone) while a branch still exists.
|
|
5513
|
+
*/
|
|
5514
|
+
function renderGitVisualTree(git) {
|
|
5515
|
+
const commits = parseGitGraphCommits(git?.graph);
|
|
5516
|
+
if (!commits.length) {
|
|
5517
|
+
if (!git?.branch) return '';
|
|
5518
|
+
return renderEmptyStateCta({
|
|
5519
|
+
headline: 'No visual tree yet',
|
|
5520
|
+
support: 'The commit graph had no parseable commit line to render.',
|
|
5521
|
+
compact: true,
|
|
5522
|
+
className: 'git-visual-tree-empty',
|
|
5523
|
+
});
|
|
5524
|
+
}
|
|
5525
|
+
const shown = commits.slice(0, MAX_GIT_VISUAL_TREE_ROWS);
|
|
5526
|
+
const rows = shown
|
|
5527
|
+
.map((c) => {
|
|
5528
|
+
const stateClass = c.isHead ? ' now-step-current' : c.isPromoted ? ' now-step-done' : '';
|
|
5529
|
+
const marker = c.isHead ? '●' : c.isPromoted ? '✓' : '○';
|
|
5530
|
+
const label = c.decoration ? escapeHtml(c.decoration) : 'Commit';
|
|
5531
|
+
const text = `<span class="now-todo-id">${escapeHtml(c.hash)}</span>${c.subject ? ` — ${escapeHtml(c.subject)}` : ''}`;
|
|
5532
|
+
return `
|
|
5533
|
+
<li class="now-step${stateClass}">
|
|
5534
|
+
<span class="now-step-marker" aria-hidden="true">${marker}</span>
|
|
5535
|
+
<div class="now-step-body">
|
|
5536
|
+
<span class="now-step-label">${label}</span>
|
|
5537
|
+
<div class="now-step-text">${text}</div>
|
|
5538
|
+
</div>
|
|
5539
|
+
</li>
|
|
5540
|
+
`;
|
|
5541
|
+
})
|
|
5542
|
+
.join('');
|
|
5543
|
+
return `
|
|
5544
|
+
<div class="git-graph-title">Visual tree (${shown.length} of ${commits.length} commit${commits.length !== 1 ? 's' : ''})</div>
|
|
5545
|
+
<ol class="now-stepper git-visual-tree" aria-label="Visual commit tree: state-colored markers by promotion status">
|
|
5546
|
+
${rows}
|
|
5547
|
+
</ol>
|
|
5548
|
+
`;
|
|
5549
|
+
}
|
|
5550
|
+
|
|
5551
|
+
/** `in_progress` / `timed_out` -> `In progress` / `Timed out`. */
|
|
5552
|
+
function humanizeRunStatus(s) {
|
|
5553
|
+
const raw = String(s || '').trim();
|
|
5554
|
+
if (!raw) return 'Unknown';
|
|
5555
|
+
return raw
|
|
5556
|
+
.split('_')
|
|
5557
|
+
.map((w) => (w ? w[0].toUpperCase() + w.slice(1) : w))
|
|
5558
|
+
.join(' ');
|
|
5559
|
+
}
|
|
5560
|
+
|
|
5561
|
+
/** Dot tone for one `gh run list` row: in-flight states read yellow; a
|
|
5562
|
+
* completed run reads by conclusion (green/red/yellow), never decorative. */
|
|
5563
|
+
function pipelineRunTone(run) {
|
|
5564
|
+
if (run.status !== 'completed') return 'yellow';
|
|
5565
|
+
if (run.conclusion === 'success') return 'green';
|
|
5566
|
+
if (['failure', 'cancelled', 'timed_out'].includes(run.conclusion)) return 'red';
|
|
5567
|
+
return 'yellow';
|
|
5568
|
+
}
|
|
5569
|
+
|
|
5570
|
+
/**
|
|
5571
|
+
* CI/CD pipeline card (Phase 2): recent `gh run list` rows, honest empty-state
|
|
5572
|
+
* when the collector didn't produce runs. Display only, no CTA — a
|
|
5573
|
+
* workflow-run URL has no named paste destination in the copy-only
|
|
5574
|
+
* convention (ADR 2026-07-25), so this card ships without one rather than
|
|
5575
|
+
* inventing a destination.
|
|
5576
|
+
*
|
|
5577
|
+
* Empty-state copy is keyed off `pipeline.reason` rather than one blanket
|
|
5578
|
+
* message: live measurement (2026-08-24, mc-git-tab-devops-pipeline-timeout
|
|
5579
|
+
* residuals) found the dominant real case is the shared snapshot budget
|
|
5580
|
+
* running out before `gh` is even attempted ('budget'), not gh being
|
|
5581
|
+
* missing/unauthenticated — the old unconditional "gh is unavailable or not
|
|
5582
|
+
* authenticated" copy misattributed that case and pointed the operator at
|
|
5583
|
+
* the wrong fix.
|
|
5584
|
+
*/
|
|
5585
|
+
function renderDevopsPipelineCard(devops) {
|
|
5586
|
+
const pipeline = devops?.pipeline || null;
|
|
5587
|
+
if (!pipeline?.available) {
|
|
5588
|
+
const support = pipeline?.reason === 'budget'
|
|
5589
|
+
? 'This snapshot ran out of time before checking recent workflow runs — refresh to retry.'
|
|
5590
|
+
: 'Recent workflow runs could not be read this snapshot (gh may be missing, unauthenticated, or the call timed out).';
|
|
5591
|
+
return renderEmptyStateCta({
|
|
5592
|
+
headline: 'No pipeline signal',
|
|
5593
|
+
support,
|
|
5594
|
+
compact: true,
|
|
5595
|
+
className: 'devops-pipeline-empty',
|
|
5596
|
+
});
|
|
5597
|
+
}
|
|
5598
|
+
const runs = pipeline.runs || [];
|
|
5599
|
+
if (!runs.length) {
|
|
5600
|
+
return renderEmptyStateCta({
|
|
5601
|
+
headline: 'No recent runs',
|
|
5602
|
+
support: 'No GitHub Actions workflow runs found for this repository.',
|
|
5603
|
+
compact: true,
|
|
5604
|
+
className: 'devops-pipeline-empty',
|
|
5605
|
+
});
|
|
5606
|
+
}
|
|
5607
|
+
const rows = runs
|
|
5608
|
+
.map((r) => {
|
|
5609
|
+
const tone = pipelineRunTone(r);
|
|
5610
|
+
const label = humanizeRunStatus(r.status === 'completed' ? r.conclusion || 'unknown' : r.status);
|
|
5611
|
+
return `
|
|
5612
|
+
<div class="devops-row">
|
|
5613
|
+
<span class="dot dot-${tone}" aria-hidden="true"></span>
|
|
5614
|
+
<span class="devops-name">${escapeHtml(r.workflow || 'Workflow')}</span>
|
|
5615
|
+
<span class="devops-meta">${escapeHtml(label)} · ${escapeHtml(r.branch || '—')} · ${escapeHtml(r.event || '—')}</span>
|
|
5616
|
+
<span class="devops-time">${escapeHtml(fmtDate(r.createdAt))}</span>
|
|
5617
|
+
</div>
|
|
5618
|
+
`;
|
|
5619
|
+
})
|
|
5620
|
+
.join('');
|
|
5621
|
+
return rows;
|
|
5622
|
+
}
|
|
5623
|
+
|
|
5624
|
+
/**
|
|
5625
|
+
* Deploy-activity card (Phase 3, best-effort, honest): a "what shipped
|
|
5626
|
+
* recently" proxy from `v*` git tags and the latest non-Unreleased CHANGELOG
|
|
5627
|
+
* entry. Deliberately not a live infra/hosting poll — no fabricated service
|
|
5628
|
+
* tiles for sources this dashboard does not actually reach.
|
|
5629
|
+
*/
|
|
5630
|
+
function renderDevopsDeployCard(devops) {
|
|
5631
|
+
const deploy = devops?.deploy || null;
|
|
5632
|
+
const tags = deploy?.tags || [];
|
|
5633
|
+
const changelog = deploy?.changelog || null;
|
|
5634
|
+
if (!tags.length && !changelog) {
|
|
5635
|
+
return renderEmptyStateCta({
|
|
5636
|
+
headline: 'No deploy signal yet',
|
|
5637
|
+
support: 'No git release tags (v*) or a parseable CHANGELOG release entry were found. This section reflects what shipped, from tags and CHANGELOG only — it does not poll live infra or hosting.',
|
|
5638
|
+
compact: true,
|
|
5639
|
+
className: 'devops-deploy-empty',
|
|
5640
|
+
});
|
|
5641
|
+
}
|
|
5642
|
+
const changelogRow = changelog
|
|
5643
|
+
? `
|
|
5644
|
+
<div class="devops-row">
|
|
5645
|
+
<span class="dot dot-green" aria-hidden="true"></span>
|
|
5646
|
+
<span class="devops-name">CHANGELOG ${escapeHtml(changelog.version)}</span>
|
|
5647
|
+
<span class="devops-meta">${escapeHtml((changelog.items || []).join(' · ') || 'Release notes')}</span>
|
|
5648
|
+
<span class="devops-time">${escapeHtml(changelog.date || '—')}</span>
|
|
5649
|
+
</div>
|
|
5650
|
+
`
|
|
5651
|
+
: '';
|
|
5652
|
+
const tagRows = tags
|
|
5653
|
+
.map(
|
|
5654
|
+
(t) => `
|
|
5655
|
+
<div class="devops-row">
|
|
5656
|
+
<span class="dot dot-gray" aria-hidden="true"></span>
|
|
5657
|
+
<span class="devops-name">${escapeHtml(t.name)}</span>
|
|
5658
|
+
<span class="devops-meta">git tag</span>
|
|
5659
|
+
<span class="devops-time">${escapeHtml(t.date || '—')}</span>
|
|
5660
|
+
</div>
|
|
5661
|
+
`,
|
|
5662
|
+
)
|
|
5663
|
+
.join('');
|
|
5664
|
+
return `
|
|
5665
|
+
<div class="devops-note">Best-effort "what shipped recently" from git tags + CHANGELOG — not a live infra/deploy poll.</div>
|
|
5666
|
+
${changelogRow}${tagRows}
|
|
5667
|
+
`;
|
|
5668
|
+
}
|
|
5669
|
+
|
|
5433
5670
|
/** Staging hygiene: untracked plan-monitor WIP (add-by-name only; ADR 2026-07-29 R14). */
|
|
5434
5671
|
function renderGitHygieneHint(git) {
|
|
5435
5672
|
const wip = git?.hygiene?.monitorWip || [];
|
|
@@ -6788,7 +7025,7 @@ function nowMetaIconSvg(kind, opts) {
|
|
|
6788
7025
|
* features >= 1 unit. Detail that cannot meet the floor is drawn filled
|
|
6789
7026
|
* (fill="currentColor" stroke="none"), never as a sub-stroke stroked shape.
|
|
6790
7027
|
* Static path markup only; never concatenate untrusted text into the SVG.
|
|
6791
|
-
* @param {'current-mission'|'monitor'|'field-report'|'checklist'|'more-sections'|'overview'|'plans'|'activity'|'agents'|'skills'|'skins'|'commands'|'health'|'git'|'memory'|'terminals'|'processes'|'config'} kind
|
|
7028
|
+
* @param {'current-mission'|'monitor'|'field-report'|'checklist'|'more-sections'|'overview'|'plans'|'activity'|'agents'|'skills'|'skins'|'commands'|'health'|'git'|'devops'|'memory'|'terminals'|'processes'|'config'} kind
|
|
6792
7029
|
* @param {{ decorative?: boolean }} [opts] decorative true (default): aria-hidden next to a visible label.
|
|
6793
7030
|
* decorative false: role=img + aria-label + title for icon-only controls (e.g. more-sections).
|
|
6794
7031
|
*/
|
|
@@ -6810,6 +7047,7 @@ function spaceIconSvg(kind, opts) {
|
|
|
6810
7047
|
commands: 'Commands',
|
|
6811
7048
|
health: 'Health',
|
|
6812
7049
|
git: 'Git',
|
|
7050
|
+
devops: 'DevOps',
|
|
6813
7051
|
memory: 'Memory',
|
|
6814
7052
|
terminals: 'Terminals',
|
|
6815
7053
|
processes: 'Processes',
|
|
@@ -6877,6 +7115,12 @@ function spaceIconSvg(kind, opts) {
|
|
|
6877
7115
|
'<path d="M10.5 4.5v7a2 2 0 01-2 2h-2"/>' +
|
|
6878
7116
|
'<path d="M6.5 11.5a2 2 0 100-4 2 2 0 000 4z"/>' +
|
|
6879
7117
|
'<path d="M10.5 6.5v2"/>',
|
|
7118
|
+
// Linked nodes (devops) — two pipeline-stage circles joined by a short
|
|
7119
|
+
// link; distinct from the Git branch glyph and from the Skills gear.
|
|
7120
|
+
devops:
|
|
7121
|
+
'<circle cx="5" cy="8" r="2.25"/>' +
|
|
7122
|
+
'<circle cx="11" cy="8" r="2.25"/>' +
|
|
7123
|
+
'<path d="M7.25 8h1.5"/>',
|
|
6880
7124
|
// Chip (memory) — two internal lines 3 units apart; a third line would drop clearance below the stroke floor
|
|
6881
7125
|
memory:
|
|
6882
7126
|
'<path d="M4.5 2.5h7a1 1 0 011 1v9a1 1 0 01-1 1h-7a1 1 0 01-1-1v-9a1 1 0 011-1z"/>' +
|
|
@@ -7779,6 +8023,24 @@ function renderUnsafe() {
|
|
|
7779
8023
|
gitDot.className = 'dot dot-green';
|
|
7780
8024
|
}
|
|
7781
8025
|
|
|
8026
|
+
// DevOps nav dot: state of the most recent pipeline run only (gray = no
|
|
8027
|
+
// signal / gh unavailable, green = latest run succeeded, yellow = latest
|
|
8028
|
+
// run in progress or non-success conclusion other than a hard failure,
|
|
8029
|
+
// red = latest run failed/cancelled/timed out).
|
|
8030
|
+
const devopsDot = document.getElementById('navDevopsDot');
|
|
8031
|
+
const latestRun = (d.devops?.pipeline?.runs || [])[0] || null;
|
|
8032
|
+
if (!latestRun) {
|
|
8033
|
+
devopsDot.className = 'dot dot-gray';
|
|
8034
|
+
} else if (latestRun.status !== 'completed') {
|
|
8035
|
+
devopsDot.className = 'dot dot-yellow';
|
|
8036
|
+
} else if (latestRun.conclusion === 'success') {
|
|
8037
|
+
devopsDot.className = 'dot dot-green';
|
|
8038
|
+
} else if (['failure', 'cancelled', 'timed_out'].includes(latestRun.conclusion)) {
|
|
8039
|
+
devopsDot.className = 'dot dot-red';
|
|
8040
|
+
} else {
|
|
8041
|
+
devopsDot.className = 'dot dot-yellow';
|
|
8042
|
+
}
|
|
8043
|
+
|
|
7782
8044
|
// Terminals / processes nav items carry count badges only (no decorative dots).
|
|
7783
8045
|
|
|
7784
8046
|
// Build full HTML string once
|
|
@@ -8169,11 +8431,33 @@ function renderUnsafe() {
|
|
|
8169
8431
|
</div>
|
|
8170
8432
|
</div>
|
|
8171
8433
|
${renderGitGraphCard(d.git)}
|
|
8434
|
+
${renderGitVisualTree(d.git)}
|
|
8172
8435
|
${d.git?.dirty ? renderGitFileList(d.git) : ''}
|
|
8173
8436
|
</div>
|
|
8174
8437
|
</div>
|
|
8175
8438
|
`);
|
|
8176
8439
|
|
|
8440
|
+
// ===== DevOps =====
|
|
8441
|
+
// Distinct scope from Processes (local-process-only): CI/CD pipeline status
|
|
8442
|
+
// + a best-effort, honestly-scoped deploy-activity proxy. No fabricated
|
|
8443
|
+
// "service health" widgets for infra this dashboard does not actually poll.
|
|
8444
|
+
const devopsPipelineRuns = d.devops?.pipeline?.runs || [];
|
|
8445
|
+
const devopsRunCount = devopsPipelineRuns.length;
|
|
8446
|
+
parts.push(`
|
|
8447
|
+
<div class="content-section" id="section-devops">
|
|
8448
|
+
<div class="section-title">
|
|
8449
|
+
DevOps
|
|
8450
|
+
<span class="section-subtitle">${devopsRunCount} pipeline run${devopsRunCount !== 1 ? 's' : ''}</span>
|
|
8451
|
+
</div>
|
|
8452
|
+
<div class="card">
|
|
8453
|
+
<div class="git-graph-title">CI/CD pipeline</div>
|
|
8454
|
+
${renderDevopsPipelineCard(d.devops)}
|
|
8455
|
+
<div class="git-graph-title">Deploy activity</div>
|
|
8456
|
+
${renderDevopsDeployCard(d.devops)}
|
|
8457
|
+
</div>
|
|
8458
|
+
</div>
|
|
8459
|
+
`);
|
|
8460
|
+
|
|
8177
8461
|
// ===== Memory =====
|
|
8178
8462
|
const recentDecisions = d.memory?.recentDecisions || [];
|
|
8179
8463
|
const recentErrors = d.memory?.recentErrors || [];
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
/** Ambient types for dashboard/lib/live-refresh.mjs (consumed by CLI TypeScript). */
|
|
2
|
+
|
|
3
|
+
export const WATCH_DEBOUNCE_MS: 400;
|
|
4
|
+
export const PERIODIC_REFRESH_MS: 15000;
|
|
5
|
+
export const SSE_SILENCE_MS: 20000;
|
|
6
|
+
export const SNAPSHOT_REPO_SOURCE_RELS: readonly string[];
|
|
7
|
+
|
|
8
|
+
export function projectSlugFromRoot(root: string): string;
|
|
9
|
+
export function resolveAgentTranscriptsWatchPath(root: string, home?: string): string;
|
|
10
|
+
export function resolveWatchPaths(root: string, dashboardDir: string): string[];
|
|
11
|
+
export function watchCoversPath(watchAbs: string, targetAbs: string): boolean;
|
|
12
|
+
export function isCoveredByWatchPaths(watchAbsPaths: string[], targetAbs: string): boolean;
|
|
13
|
+
export function createTrailingDebounce(
|
|
14
|
+
fn: () => void,
|
|
15
|
+
ms: number,
|
|
16
|
+
timers?: {
|
|
17
|
+
setTimeout?: typeof setTimeout;
|
|
18
|
+
clearTimeout?: typeof clearTimeout;
|
|
19
|
+
now?: () => number;
|
|
20
|
+
maxWait?: number;
|
|
21
|
+
},
|
|
22
|
+
): () => void;
|
|
23
|
+
export function isSseSilent(lastEventAt: number, now: number, silenceMs?: number): boolean;
|
|
@@ -24,10 +24,17 @@ export const MONITOR_FEED_CAP = 20;
|
|
|
24
24
|
/** Cap agent_step rows emitted per active plan for the denser Crew feed. */
|
|
25
25
|
export const MONITOR_AGENT_STEP_EMIT_CAP = 12;
|
|
26
26
|
|
|
27
|
-
/**
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
27
|
+
/**
|
|
28
|
+
* Cap subagent-run and plan_review pointer rows emitted per snapshot (fs scan
|
|
29
|
+
* bounds for the former live in dashboard-data.mjs). Halved from 8/4 (C-G3,
|
|
30
|
+
* plan-monitor-crew-monitor-compact-labels-realtime-activity-2026-08-05.md):
|
|
31
|
+
* at full caps the two kinds sat ahead of `plan_progress` in mergeActivity's
|
|
32
|
+
* priority concat and could claim 12 of MONITOR_FEED_CAP's 20 slots during a
|
|
33
|
+
* busy run-plan-all batch, squeezing out plan-progress rows. 4/2 leaves more
|
|
34
|
+
* headroom without reordering the merge itself.
|
|
35
|
+
*/
|
|
36
|
+
export const MONITOR_SUBAGENT_EMIT_CAP = 4;
|
|
37
|
+
export const MONITOR_PLAN_REVIEW_EMIT_CAP = 2;
|
|
31
38
|
|
|
32
39
|
/**
|
|
33
40
|
* Monitor hero curated subset over the semantic activity stream.
|
|
@@ -2511,7 +2518,7 @@ export function formatPlanReviewActivity(
|
|
|
2511
2518
|
label: truncateStr(visible, MAX_SEMANTIC_LABEL),
|
|
2512
2519
|
labelFull: visible,
|
|
2513
2520
|
sourcePath: report.path || null,
|
|
2514
|
-
refs: { plan:
|
|
2521
|
+
refs: { plan: planRef, report: report.file, triaged },
|
|
2515
2522
|
});
|
|
2516
2523
|
}
|
|
2517
2524
|
return events;
|