create-pmos 0.524.0 → 0.526.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/package.json +57 -56
- package/payload/KIT-VERSION +1 -1
- package/payload/planning/evals/eval-calibration.md +1 -1
- package/payload/planning/okrs/health-budgets.md +1 -1
- package/payload/state/discoveries.md +1 -1
- package/workspace/briefing-premium-board-test.js +1 -1
- package/workspace/changelog.json +56 -0
- package/workspace/ev-everywhere-test.js +2 -2
- package/workspace/guide/agent-capabilities.md +28 -2
- package/workspace/guide/board.md +14 -1
- package/workspace/guide/claude-proposes.md +3 -1
- package/workspace/guide/data-freshness.md +13 -0
- package/workspace/guide/home.md +11 -5
- package/workspace/guide/idle-lab.md +2 -2
- package/workspace/guide/lifecycle.md +16 -3
- package/workspace/guide/published-board.md +2 -0
- package/workspace/guide/today.md +11 -3
- package/workspace/lib/bg-queue.js +7 -3
- package/workspace/lib/board-premium.js +4 -1
- package/workspace/lib/board-publish-parts.js +14 -2
- package/workspace/lib/engine/boards.js +3 -2
- package/workspace/lib/headless.js +19 -4
- package/workspace/lib/idle-lab-engine.js +531 -0
- package/workspace/lib/initiative-chat.js +12 -2
- package/workspace/lib/initiative-cli.js +1 -1
- package/workspace/lib/initiative-premium.js +11 -3
- package/workspace/lib/lab-cli.js +220 -0
- package/workspace/lib/lifecycle-stage.js +17 -3
- package/workspace/lib/one-stage.js +131 -0
- package/workspace/lib/pmos-verbs.js +6 -0
- package/workspace/lib/proposals.js +5 -2
- package/workspace/lib/read-fingerprint.js +127 -0
- package/workspace/lib/refresh-cli.js +75 -0
- package/workspace/lib/refresh-probe.js +110 -0
- package/workspace/lib/refresh-run.js +133 -14
- package/workspace/lib/report-draft.js +1 -1
- package/workspace/lib/route-modules.js +1 -0
- package/workspace/lib/routes-board-premium.js +22 -0
- package/workspace/lib/routes-boards.js +61 -12
- package/workspace/lib/routes-notes.js +1 -1
- package/workspace/lib/routes-your-move.js +64 -0
- package/workspace/lib/status-signal.js +123 -0
- package/workspace/lib/workflow-cli.js +3 -1
- package/workspace/lib/your-move.js +61 -0
- package/workspace/package-lock.json +2 -2
- package/workspace/package.json +1 -1
- package/workspace/public/pm/bd-acts.js +2 -1
- package/workspace/public/pm/bd-cols.js +8 -5
- package/workspace/public/pm/bd-prog-panel.js +3 -2
- package/workspace/public/pm/bd-span.js +2 -1
- package/workspace/public/pm/bd-views.js +8 -6
- package/workspace/public/pm/cozy-home.css +3 -0
- package/workspace/public/pm/cozy-today.css +151 -0
- package/workspace/public/pm/cozy.css +9 -0
- package/workspace/public/pm/good-morning.js +327 -0
- package/workspace/public/pm/grill-words.js +16 -1
- package/workspace/public/pm/home-app.js +187 -18
- package/workspace/public/pm/home-data.js +45 -13
- package/workspace/public/pm/home-day.js +66 -14
- package/workspace/public/pm/home-ini-model.js +1 -1
- package/workspace/public/pm/home-stage-card.js +7 -0
- package/workspace/public/pm/ini-tasks.js +2 -2
- package/workspace/public/pm/ini-view-model.js +10 -3
- package/workspace/public/pm/ini-view.css +9 -0
- package/workspace/public/pm/ini-view.js +19 -5
- package/workspace/public/pm/move-rank.js +155 -0
- package/workspace/public/pm/premium-board.js +10 -6
- package/workspace/public/pm/premium-initiative-head.js +39 -4
- package/workspace/public/pm/readonly-boot.js +8 -0
- package/workspace/public/pm/stage-chip.js +44 -0
- package/workspace/run-tests.js +1 -0
- package/workspace/server.js +63 -1
- package/workspace/skills/calendar-sync.skill +2 -1
- package/workspace/skills/idle-lab-prototype.skill +36 -0
- package/workspace/skills/idle-lab-scan.skill +32 -0
- package/workspace/skills/jira-sync.skill +2 -1
- package/workspace/skills/my-work-read.skill +2 -1
- package/workspace/skills/sources-read.skill +9 -6
- package/workspace/test-lists/good-morning.json +9 -0
- package/workspace/test-lists/idle-lab-engine.json +9 -0
- package/workspace/test-lists/one-stage.json +5 -0
- package/workspace/test-lists/status-signal.json +5 -0
- package/workspace/test-lists/your-move.json +9 -0
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "create-pmos",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.526.0",
|
|
4
4
|
"description": "Scaffold the PMOS portable kit — run the PMOS product-management workflow (initiative → lane-fit spec → contract → build → three gates, with work-type lanes for features, research, maintenance, incidents, and content) entirely inside your own repo, with all state as git-versioned files. Includes `workflow-sweep`, which audits the state every board derives from and separates real defects from work you simply have not done. `create-pmos workspace` also installs + launches the local Terminal Workspace GUI. No database, no network, no telemetry.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"bin": {
|
|
@@ -32,6 +32,62 @@
|
|
|
32
32
|
"audit"
|
|
33
33
|
],
|
|
34
34
|
"pmosChanges": [
|
|
35
|
+
{
|
|
36
|
+
"v": "0.526.0",
|
|
37
|
+
"at": "2026-11-04T10:37:51.951Z",
|
|
38
|
+
"f": 4,
|
|
39
|
+
"prs": [
|
|
40
|
+
{
|
|
41
|
+
"n": 1226,
|
|
42
|
+
"t": "Your move is one ranked list of every open ✦, with ages (workspace grill W3)",
|
|
43
|
+
"s": "Your move is one ranked list of every open ✦, with ages (workspace grill W3)",
|
|
44
|
+
"k": "new"
|
|
45
|
+
},
|
|
46
|
+
{
|
|
47
|
+
"n": 1225,
|
|
48
|
+
"t": "Status says what it knows — On track only from a read (workspace grill W2)",
|
|
49
|
+
"s": "Status says what it knows — On track only from a read (workspace grill W2)",
|
|
50
|
+
"k": "new"
|
|
51
|
+
},
|
|
52
|
+
{
|
|
53
|
+
"n": 1236,
|
|
54
|
+
"t": "Idle lab engine — prototypes and scans while the PM is away (idle lab build E)",
|
|
55
|
+
"s": "Idle lab engine — prototypes and scans while the PM is away (idle lab build E)",
|
|
56
|
+
"k": "new"
|
|
57
|
+
},
|
|
58
|
+
{
|
|
59
|
+
"n": 1230,
|
|
60
|
+
"t": "One true stage per initiative, read from the real workflow (workspace grill W1)",
|
|
61
|
+
"s": "One true stage per initiative, read from the real workflow (workspace grill W1)",
|
|
62
|
+
"k": "new"
|
|
63
|
+
},
|
|
64
|
+
{
|
|
65
|
+
"n": 1235,
|
|
66
|
+
"t": "Good morning is one page — the quarter first, then today, then time",
|
|
67
|
+
"s": "Good morning is one page — the quarter first, then today, then time",
|
|
68
|
+
"k": "new"
|
|
69
|
+
}
|
|
70
|
+
]
|
|
71
|
+
},
|
|
72
|
+
{
|
|
73
|
+
"v": "0.525.0",
|
|
74
|
+
"at": "2026-11-04T09:08:28.453Z",
|
|
75
|
+
"f": 4,
|
|
76
|
+
"prs": [
|
|
77
|
+
{
|
|
78
|
+
"n": 1231,
|
|
79
|
+
"t": "Smart refresh steps 1 and 2: measure each read, ask first, share one session",
|
|
80
|
+
"s": "Smart refresh steps 1 and 2: measure each read, ask first, share one session",
|
|
81
|
+
"k": "new"
|
|
82
|
+
},
|
|
83
|
+
{
|
|
84
|
+
"n": 1233,
|
|
85
|
+
"t": "Two programs in one link keep both, each tab on its own product",
|
|
86
|
+
"s": "Two programs in one link keep both, each tab on its own product",
|
|
87
|
+
"k": "fix"
|
|
88
|
+
}
|
|
89
|
+
]
|
|
90
|
+
},
|
|
35
91
|
{
|
|
36
92
|
"v": "0.524.0",
|
|
37
93
|
"at": "2026-11-04T08:57:48.087Z",
|
|
@@ -359,61 +415,6 @@
|
|
|
359
415
|
"d": "Moving a date or cutting a task can quietly break a milestone. Now, before you approve a plan, Claude walks through the change and shows what it breaks or helps. Nothing changes until you say yes."
|
|
360
416
|
}
|
|
361
417
|
]
|
|
362
|
-
},
|
|
363
|
-
{
|
|
364
|
-
"v": "0.506.0",
|
|
365
|
-
"at": "2026-11-03T12:14:24.342Z",
|
|
366
|
-
"f": 4,
|
|
367
|
-
"prs": [
|
|
368
|
-
{
|
|
369
|
-
"n": 1191,
|
|
370
|
-
"t": "Ai-guard, one guard for every AI job",
|
|
371
|
-
"s": "Ai-guard, one guard for every AI job",
|
|
372
|
-
"k": "new",
|
|
373
|
-
"h": "One switch for every AI job",
|
|
374
|
-
"d": "Claude runs several jobs in the background, each on its own. Now one shared guard sits in front of all of them, so you can pause them all in a single step."
|
|
375
|
-
},
|
|
376
|
-
{
|
|
377
|
-
"n": 1193,
|
|
378
|
-
"t": "Decision memory, the grill's earlier-decision angle",
|
|
379
|
-
"s": "Decision memory, the grill's earlier-decision angle",
|
|
380
|
-
"k": "new",
|
|
381
|
-
"h": "Earlier decisions come back",
|
|
382
|
-
"d": "A grill could forget something you decided weeks ago. Now, when you grill something similar, Claude brings up what you decided before."
|
|
383
|
-
},
|
|
384
|
-
{
|
|
385
|
-
"n": 1195,
|
|
386
|
-
"t": "Ask PMOS about the past, with the record behind every answer",
|
|
387
|
-
"s": "Ask PMOS about the past, with the record behind every answer",
|
|
388
|
-
"k": "new",
|
|
389
|
-
"h": "Ask PMOS about the past",
|
|
390
|
-
"d": "You could not ask why a plan changed or what an earlier grill decided. Now you can, and every answer shows the record it came from, so you can check it.",
|
|
391
|
-
"top": "Claude now remembers earlier decisions and answers questions about the past, with the record behind every answer."
|
|
392
|
-
},
|
|
393
|
-
{
|
|
394
|
-
"n": 1192,
|
|
395
|
-
"t": "What would I have missed, a weekly check for quiet drift",
|
|
396
|
-
"s": "What would I have missed, a weekly check for quiet drift",
|
|
397
|
-
"k": "new",
|
|
398
|
-
"h": "A weekly check for quiet drift",
|
|
399
|
-
"d": "Work can slide away from its goal without anyone noticing. Now, once a week, Claude looks and tells you what you would have missed, with the evidence."
|
|
400
|
-
}
|
|
401
|
-
]
|
|
402
|
-
},
|
|
403
|
-
{
|
|
404
|
-
"v": "0.505.0",
|
|
405
|
-
"at": "2026-11-03T11:01:41.523Z",
|
|
406
|
-
"f": 4,
|
|
407
|
-
"prs": [
|
|
408
|
-
{
|
|
409
|
-
"n": 1190,
|
|
410
|
-
"t": "Finish a recording from any tab that shows it",
|
|
411
|
-
"s": "Finish a recording from any tab that shows it",
|
|
412
|
-
"k": "fix",
|
|
413
|
-
"h": "Finish a recording from any tab",
|
|
414
|
-
"d": "A recording could only be finished from the tab that started it. Now any tab that shows it can finish it."
|
|
415
|
-
}
|
|
416
|
-
]
|
|
417
418
|
}
|
|
418
419
|
]
|
|
419
420
|
}
|
package/payload/KIT-VERSION
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
type: Reference
|
|
3
3
|
title: "Eval calibration log"
|
|
4
4
|
description: "Append-only record of every PM override of an evaluator verdict."
|
|
5
|
-
generated: {by: process:create-pmos, at: "2026-11-
|
|
5
|
+
generated: {by: process:create-pmos, at: "2026-11-04T10:37:49Z"}
|
|
6
6
|
status: stable
|
|
7
7
|
---
|
|
8
8
|
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
type: Reference
|
|
3
3
|
title: "Health budgets"
|
|
4
4
|
description: "Closed registry of health-budget anchors (D59), edited only by the PM."
|
|
5
|
-
generated: {by: process:create-pmos, at: "2026-11-
|
|
5
|
+
generated: {by: process:create-pmos, at: "2026-11-04T10:37:49Z"}
|
|
6
6
|
status: stable
|
|
7
7
|
---
|
|
8
8
|
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
type: Reference
|
|
3
3
|
title: "Discoveries and friction log"
|
|
4
4
|
description: "Append-only record of what runs discovered and where the process rubbed."
|
|
5
|
-
generated: {by: process:create-pmos, at: "2026-11-
|
|
5
|
+
generated: {by: process:create-pmos, at: "2026-11-04T10:37:49Z"}
|
|
6
6
|
status: stable
|
|
7
7
|
---
|
|
8
8
|
|
|
@@ -561,7 +561,7 @@ const IVREAD = () => {
|
|
|
561
561
|
while (Date.now() - t0 < 90000) { const r = await fetch(BASE + '/api/board-premium'); j = await r.json(); if (j.state === 'ready' || j.state === 'error') break; if (r.status !== 202) break; await sleep(1500); }
|
|
562
562
|
ok('E1 the real route answers "reading" first and then the board of this repository', !!j && j.ok && j.state === 'ready' && j.model.board.name.length > 0, JSON.stringify(j).slice(0, 200));
|
|
563
563
|
const m = j && j.model;
|
|
564
|
-
ok('E2 the real model\'s counts agree with each other: the header, the dock and the late and at-risk rows', !!m && m.dock.needs === m.initiatives.risk + m.initiatives.late && m.initiatives.on + m.initiatives.risk + m.initiatives.late + m.initiatives.hold === m.initiatives.open && m.initiatives.list.rows.slice(0, 5).every((r) => r.bad || m.initiatives.risk + m.initiatives.late === 0), m ? JSON.stringify(m.initiatives).slice(0, 200) : '');
|
|
564
|
+
ok('E2 the real model\'s counts agree with each other (no signal counted apart, workspace grill W2): the header, the dock and the late and at-risk rows', !!m && m.dock.needs === m.initiatives.risk + m.initiatives.late && m.initiatives.on + m.initiatives.risk + m.initiatives.late + m.initiatives.hold + (m.initiatives.none || 0) === m.initiatives.open && m.initiatives.list.rows.slice(0, 5).every((r) => r.bad || m.initiatives.risk + m.initiatives.late === 0), m ? JSON.stringify(m.initiatives).slice(0, 200) : '');
|
|
565
565
|
ok('E3 the real model draws no sprint and no release without a source, and no demo data', !!m && !m.sprint.name && !m.release.at && !/demo/i.test(JSON.stringify({ h: m.header, s: m.sprint, r: m.release, d: m.docs, b: m.board })));
|
|
566
566
|
ok('E3 the real model has the eight steps and a track on every row', !!m && m.steps.length === 8 && m.initiatives.list.rows.every((r) => r.track && typeof r.track.k === 'number'));
|
|
567
567
|
const post = await fetch(BASE + '/api/board-premium', { method: 'POST', headers: await T.pressHeaders(BASE), body: '{}' }).then((r) => r.status);
|
package/workspace/changelog.json
CHANGED
|
@@ -1,4 +1,60 @@
|
|
|
1
1
|
[
|
|
2
|
+
{
|
|
3
|
+
"v": "0.526.0",
|
|
4
|
+
"at": "2026-11-04T10:37:51.951Z",
|
|
5
|
+
"f": 4,
|
|
6
|
+
"prs": [
|
|
7
|
+
{
|
|
8
|
+
"n": 1226,
|
|
9
|
+
"t": "Your move is one ranked list of every open ✦, with ages (workspace grill W3)",
|
|
10
|
+
"s": "Your move is one ranked list of every open ✦, with ages (workspace grill W3)",
|
|
11
|
+
"k": "new"
|
|
12
|
+
},
|
|
13
|
+
{
|
|
14
|
+
"n": 1225,
|
|
15
|
+
"t": "Status says what it knows — On track only from a read (workspace grill W2)",
|
|
16
|
+
"s": "Status says what it knows — On track only from a read (workspace grill W2)",
|
|
17
|
+
"k": "new"
|
|
18
|
+
},
|
|
19
|
+
{
|
|
20
|
+
"n": 1236,
|
|
21
|
+
"t": "Idle lab engine — prototypes and scans while the PM is away (idle lab build E)",
|
|
22
|
+
"s": "Idle lab engine — prototypes and scans while the PM is away (idle lab build E)",
|
|
23
|
+
"k": "new"
|
|
24
|
+
},
|
|
25
|
+
{
|
|
26
|
+
"n": 1230,
|
|
27
|
+
"t": "One true stage per initiative, read from the real workflow (workspace grill W1)",
|
|
28
|
+
"s": "One true stage per initiative, read from the real workflow (workspace grill W1)",
|
|
29
|
+
"k": "new"
|
|
30
|
+
},
|
|
31
|
+
{
|
|
32
|
+
"n": 1235,
|
|
33
|
+
"t": "Good morning is one page — the quarter first, then today, then time",
|
|
34
|
+
"s": "Good morning is one page — the quarter first, then today, then time",
|
|
35
|
+
"k": "new"
|
|
36
|
+
}
|
|
37
|
+
]
|
|
38
|
+
},
|
|
39
|
+
{
|
|
40
|
+
"v": "0.525.0",
|
|
41
|
+
"at": "2026-11-04T09:08:28.453Z",
|
|
42
|
+
"f": 4,
|
|
43
|
+
"prs": [
|
|
44
|
+
{
|
|
45
|
+
"n": 1231,
|
|
46
|
+
"t": "Smart refresh steps 1 and 2: measure each read, ask first, share one session",
|
|
47
|
+
"s": "Smart refresh steps 1 and 2: measure each read, ask first, share one session",
|
|
48
|
+
"k": "new"
|
|
49
|
+
},
|
|
50
|
+
{
|
|
51
|
+
"n": 1233,
|
|
52
|
+
"t": "Two programs in one link keep both, each tab on its own product",
|
|
53
|
+
"s": "Two programs in one link keep both, each tab on its own product",
|
|
54
|
+
"k": "fix"
|
|
55
|
+
}
|
|
56
|
+
]
|
|
57
|
+
},
|
|
2
58
|
{
|
|
3
59
|
"v": "0.524.0",
|
|
4
60
|
"at": "2026-11-04T08:57:48.087Z",
|
|
@@ -118,10 +118,10 @@ const put = (root, rel, text) => { fs.mkdirSync(path.dirname(path.join(root, rel
|
|
|
118
118
|
posts.length = 0;
|
|
119
119
|
const nfy = (await json('GET', '/api/news-for-you?ws=' + encodeURIComponent(ws))).body || {};
|
|
120
120
|
await pg.click('#hmList [data-hm-day]');
|
|
121
|
-
const yd = await until(() => pg.evaluate(() => { const v = document.querySelector('#czViewer:not([hidden])'); if (!v || !v.querySelector('.yd')) return null; const f = v.querySelector('.
|
|
121
|
+
const yd = await until(() => pg.evaluate(() => { const v = document.querySelector('#czViewer:not([hidden])'); if (!v || !v.querySelector('.yd')) return null; const f = v.querySelector('.gm-since');
|
|
122
122
|
return { cal: !!v.querySelector('.cz-vw-hd [data-cz-vw-p="cal"]'), more: !!v.querySelector('.cz-vw-hd [data-cz-vw="more"]'), fold: !!f, rows: f ? f.querySelectorAll('[data-yd="news"]').length : 0, all: !!(f && f.querySelector('[data-yd="seen"]')) }; }), 20000);
|
|
123
123
|
ok('N1 Good morning opens Your day, with the calendar as an icon in its header and no ⋯', !!yd && yd.cal && !yd.more, JSON.stringify(yd));
|
|
124
|
-
ok('N1 New for you is
|
|
124
|
+
ok('N1 New for you is Good morning’s Since yesterday (nyt-ui GM2): the newest 3 at most, with ✓✓; nothing new draws no block', !!yd && (nfy.count > 0 ? yd.fold && yd.rows === Math.min(3, nfy.count) && yd.all : !yd.fold), JSON.stringify({ yd, count: nfy.count }));
|
|
125
125
|
ok('N1 the place menu no longer opens a New for you page', await pg.evaluate(() => !document.querySelector('#czMenu [data-cz-news]')));
|
|
126
126
|
const own = posts.filter((u) => u !== '/api/loose-props/rows');
|
|
127
127
|
ok('N1 opening Your day posted nothing', own.length === 0, JSON.stringify(posts));
|
|
@@ -18,7 +18,7 @@ This page lists every job, so you know what runs and why. Each row links to the
|
|
|
18
18
|
- **Few at a time.** A run shows at most 3 proposals. In a quiet week it shows nothing.
|
|
19
19
|
- **Tested first.** A new version of a job shows nothing until its replay passes: its own known cases, and the guard's own cases (a made-up quote, a missing source, a path outside the repository, a write key). Each of those must be dropped.
|
|
20
20
|
- **Your login, your connections.** A job runs as a background Claude session with your own login, model, profile and connectors. The workspace holds no password or token. `PMOS_HEADLESS=off` sends every job back to a terminal pane.
|
|
21
|
-
- **One queue.** Every background job waits for its turn in one queue. Each minute the jobs go in this order: what is due at a set time (schedules, the morning brief and day check, the data refresh, report schedules), then the Initiative Driver, then the deep drafts (core documents, Your impact, metric drafts and reads, grill, proposals), then the idle work (the Horizon scan). What you ask for, such as Scan now or Prepare my day, starts at once and never waits in the queue.
|
|
21
|
+
- **One queue.** Every background job waits for its turn in one queue. Each minute the jobs go in this order: what is due at a set time (schedules, the morning brief and day check, the data refresh, report schedules), then the Initiative Driver, then the deep drafts (core documents, Your impact, metric drafts and reads, grill, proposals), then the idle work (the Horizon scan, then the idle lab). What you ask for, such as Scan now or Prepare my day, starts at once and never waits in the queue.
|
|
22
22
|
- **One run for each initiative.** A background run never starts on an initiative that another background run is working on. It tries again a minute later.
|
|
23
23
|
- **Idle work waits for you to step away.** The idle work starts only when you have not used PMOS for 30 minutes, or in the last hour of your working day if you never stepped away. It also waits when 3 background runs are live, inside quiet hours, and at the spending limit.
|
|
24
24
|
- **Your hours.** Scheduled jobs run inside your working hours and never inside your quiet hours.
|
|
@@ -38,6 +38,7 @@ This page lists every job, so you know what runs and why. Each row links to the
|
|
|
38
38
|
| [Expected outcomes](outcomes.md) | Once a day. At most 3 drafts a day for each product. | The PRD's success criteria, or the anchored key result | "Expected outcome" under the initiative's ✦. Today when a check is due. | `pmos ai off outcomes`. `PMOS_OUTCOMES=off` |
|
|
39
39
|
| [Metric drafts](metric-drafts.md) | A product with no North Star, the first 14 days of a quarter, a program with no goal, and an initiative that gets a PRD | The last 8 weeks of real readings | The page of that product, program or initiative | `PMOS_METRIC_DRAFT=off` |
|
|
40
40
|
| [Horizon scan](horizon-scan.md) | Daily by default, at most once a day, the first time you step away after 09:00. Scan now: at most 3 a day. | The public web for your kept watch list, and your repository | Report documents and proposals you approve | Cadence: Off. `PMOS_SCAN=off` |
|
|
41
|
+
| Idle lab | When you have not used PMOS for 30 minutes. One run at a time, at most 3 results each time you step away. | Prototypes: the initiative's record, PRD and earlier specimens. Scans: public pages only, read through `pmos lab page`, and no repository. | "Claude prototyped it", "Claude improved it" and "Claude scanned for it" under the initiative's ✦. A finding that fits no initiative: Intelligence › Lab. | `pmos ai off idle-lab` |
|
|
41
42
|
| [What you might have missed](what-you-missed.md) | Each Monday, for the week before. It uses no model. | Records only: tasks, dates, initiatives and Jira status | One ✦ in Home's chat, at most 3 items | `pmos ai off drift`. `PMOS_DRIFT=off` |
|
|
42
43
|
| [Your impact](your-impact.md) | Claude reads once a day. Home shows the week after it ends. | Slack, mail, Jira, your meeting notes, your documents and your key results | Adler's sprout on Home, and your impact log | Settings › General › Your impact. `PMOS_IMPACT=off` |
|
|
43
44
|
| [Morning brief and day check](proactive-engine.md) | The morning brief at 06:45, once you schedule it. The day check every 60 minutes by default (30, 60 or off). | Calendar, Wispr Flow, Slack, Jira and Confluence are on by default. Mail, GitHub, Drive, Figma and websites are off by default. Mail: subjects and senders only. | Today | Each source is a setting. `pmos proactive settings` |
|
|
@@ -74,4 +75,29 @@ When you ask an agent session to do a piece of work, it can finish it, including
|
|
|
74
75
|
- `pmos ai log [<job>]`: the last audit lines. Each dropped proposal shows why.
|
|
75
76
|
- `pmos ai off [<job>]` and `pmos ai on [<job>]`: turn every AI job, or one job, off or on. `PMOS_AI=off` in the environment wins over the setting.
|
|
76
77
|
|
|
77
|
-
The AI jobs are `past-repeat`, `decision-memory`, `outcomes`, `descriptions`, `drift`, `rehearse`, `next-prompt` and `
|
|
78
|
+
The AI jobs are `past-repeat`, `decision-memory`, `outcomes`, `descriptions`, `drift`, `rehearse`, `next-prompt`, `sharpen-prompt` and `idle-lab`. The switch also covers each job in the queue by its queue name: `schedules`, `proactive`, `prepare`, `day`, `refresh`, `reports`, `driver`, `finder`, `coredocs`, `milestones`, `propose`, `grill`, `metric-drafts`, `impact`, `metric-reads`, `forecast`, `report-design`, `report-structure`, `scan` and `idle-lab`. `pmos ai off` with no job stops all of them. Git sync uses no model, so the switch does not stop it. A background run cannot change the switch.
|
|
79
|
+
|
|
80
|
+
## The idle lab
|
|
81
|
+
|
|
82
|
+
When you step away, Claude does one of these for your initiatives, in this order:
|
|
83
|
+
|
|
84
|
+
1. **Improve a prototype.** You dropped a round with a reason, or a grill or scan finding came in after the last round. Claude makes one new round of one specimen and says what changed. It never starts a new round while one waits for you.
|
|
85
|
+
2. **Prototype a new idea.** An initiative in Triage or Discover whose specimen test says a description is not enough, and that has no prototype yet. Claude makes 2 or 3 different specimens.
|
|
86
|
+
3. **Scan for something new.** A kept watch item that no scan read in 14 days, or an early initiative that nobody looked outside for.
|
|
87
|
+
4. **Refresh an old scan.** A scan finding that is 14 days old. Claude keeps only what is new since then.
|
|
88
|
+
|
|
89
|
+
Before you see a result, PMOS proves it:
|
|
90
|
+
|
|
91
|
+
- Each specimen must open and render in a headless browser on this computer, with the network shut. With no headless browser, no prototype is shown.
|
|
92
|
+
- Each claim must quote what was read: a prototype quotes the initiative's own words at `path:line`, and a scan quotes a line of a page the run read.
|
|
93
|
+
- What is not proven is dropped, and the reason is logged. `pmos lab status` shows this month's runs, and `pmos ai log idle-lab` shows each drop.
|
|
94
|
+
|
|
95
|
+
Specimens stay in the runtime folder on this computer. Nothing goes into a product repository before your ✓. The idle lab's spend counts toward the same limit as the grill in Settings › Claude's checks.
|
|
96
|
+
|
|
97
|
+
The run uses only these commands:
|
|
98
|
+
|
|
99
|
+
- `pmos lab page <url>`: a scan run reads one public page. PMOS refuses a private or local address and keeps the page text, so a quote can be checked.
|
|
100
|
+
- `pmos lab file <group> --json -`: a run files one result. It waits until the run ends and the proof passes.
|
|
101
|
+
- `pmos lab status`: in a run, what it filed. Outside a run, this month's idle lab runs and spend.
|
|
102
|
+
|
|
103
|
+
Not proven yet: the compare view's Production and Design columns stay left out until PMOS shows on your computer that it can render production from the product repository and read the design.
|
package/workspace/guide/board.md
CHANGED
|
@@ -2,13 +2,26 @@
|
|
|
2
2
|
type: Guide
|
|
3
3
|
title: "pmos board: the items of every initiative"
|
|
4
4
|
description: "How pmos board prints the items of every initiative in four columns from a terminal, and where the workspace shows initiatives and their tasks."
|
|
5
|
-
timestamp: 2026-11-
|
|
5
|
+
timestamp: 2026-11-04
|
|
6
6
|
---
|
|
7
7
|
|
|
8
8
|
# pmos board: the items of every initiative
|
|
9
9
|
|
|
10
10
|
The **Board** place of the workspace shows initiatives, not items: every initiative of the products you pick, by stage, with programs, a timeline and a list. [Programs on the Board](programs.md) explains it. An initiative's tasks show under it in Home's list and in the initiative's page in the Viewer.
|
|
11
11
|
|
|
12
|
+
## What an initiative's status means
|
|
13
|
+
|
|
14
|
+
The status of an initiative tells only what PMOS read. If PMOS read nothing, the status is **No signal**.
|
|
15
|
+
|
|
16
|
+
- **On track**: a Jira read from the last 14 days shows no ticket past its due date or sprint end, or the plan items have dates that are still ahead.
|
|
17
|
+
- **Late**: a date passed. This is the planned finish of the plan items, or a milestone.
|
|
18
|
+
- **At risk**: a read found a problem, or you confirmed a risk. A problem is an overdue item, a blocked or late Jira ticket, or work that is idle. To confirm a risk, press ✓ on Claude's "Mark … at risk" suggestion for a program milestone.
|
|
19
|
+
- **No signal** (grey): PMOS read nothing that tells how the work goes. No signal never counts as on track.
|
|
20
|
+
|
|
21
|
+
To read Jira for the initiatives with no signal, open **Needs a look** and press **✦ Read Jira now**.
|
|
22
|
+
|
|
23
|
+
The weekly update in Home follows the same rules. Claude drafts it only when something moved this week or a risk is open. The update starts with **Before you send**: the risks that Claude found and you did not confirm. Press ✓ to confirm all of them. The mail does not include these risks. The initiatives with no signal are under **Not read**.
|
|
24
|
+
|
|
12
25
|
The command below prints the items themselves, from a terminal.
|
|
13
26
|
|
|
14
27
|
## From a terminal
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
type: Guide
|
|
3
3
|
title: "Claude proposes: the one ✦ on each initiative"
|
|
4
4
|
description: "What Claude finds when you add an initiative that already lives elsewhere, the new dates, done and tidy names it proposes for late tasks, the clean-up of the work that is not in an initiative, how you keep or drop them in the Viewer, Undo, the pmos propose commands, and how Claude grills an initiative by itself (pmos grill)."
|
|
5
|
-
timestamp: 2026-11-
|
|
5
|
+
timestamp: 2026-11-04
|
|
6
6
|
---
|
|
7
7
|
|
|
8
8
|
# Claude proposes: the one ✦ on each initiative
|
|
@@ -71,6 +71,8 @@ You can also start one any time: in the initiative's chat, write "grill this" (o
|
|
|
71
71
|
|
|
72
72
|
Each finding is a proposal in the group "Claude grilled it", under the same ✦. Each row shows the mark and the name of the angle that found it: Premortem, Red team, Voices, Reframe, Scope, What-if or Earlier decision. Voices are simulated from your stored research and meeting notes, only with 3 sources or more, and carry the tag "Simulated, not evidence". A What-if carries "Simulated, not the plan". Each finding ends with one next step. ✓ adds that step as a task. ✎ lets you write the step in your own words first; ✓ then adds your words. ✕ drops the finding. A finding never rides on the header's ✓. Above the findings, one quiet line names the angles Claude chose, when and why it ran, and what the run cost. Three findings show at a time; "+N smaller findings" and its ⋯ show the rest. On a phone the findings are cards side by side: swipe for the next. With no findings, nothing shows.
|
|
73
73
|
|
|
74
|
+
The initiative's header shows its two strongest findings, each with its angle and day, and a ✦ with the count that opens all of them. Every finding, including the ones behind "+N smaller findings", is also ranked in Your move in [Your day](today.md).
|
|
75
|
+
|
|
74
76
|
When Claude grilled an initiative this week and left findings, Home says so in one line under "Good morning", and its ✦ opens the findings. When it grilled more than one, the line names the newest and says how many more, for example "I grilled Inline login and 5 more this week: 21 findings." The others' findings are under each initiative's own ✦. When a key result will miss its goal, or drifted to at risk, Intelligence's ✦ line names it and the initiative Claude grilled for it; its ✦ opens those findings.
|
|
75
77
|
|
|
76
78
|
### Earlier decision: Claude remembers what you decided
|
|
@@ -97,6 +97,19 @@ The skill saves its reads with this command:
|
|
|
97
97
|
|
|
98
98
|
The reads are kept in your own runtime folder on this machine, never in a repository.
|
|
99
99
|
|
|
100
|
+
### Ask first, read in full only when something changed
|
|
101
|
+
|
|
102
|
+
A read of Calendar, Jira, work assigned to you or Your tools first asks the tool one short question: did anything change since the last read? If nothing changed, the read keeps what PMOS already stored and only moves its read time to now. If something changed, it reads in full as before. Once a day the read is always in full, because a question about changes can miss something, such as a meeting that moved into the next 14 days.
|
|
103
|
+
|
|
104
|
+
When two or more of these reads are due at the same minute, they run in one session, one after another, instead of one session each. A read that the session did not save is written as failed, with that reason, and is tried again like any failed read.
|
|
105
|
+
|
|
106
|
+
The skills use these commands:
|
|
107
|
+
|
|
108
|
+
- `pmos refresh since <source>` says **ask first** or **read in full**, with the reason and the time of the last read. `<source>` is calendar, jira, mywork or tools.
|
|
109
|
+
- `pmos refresh same <source>` keeps the stored read as it is and moves its read time to now. For Your tools, `--only slack,mail` confirms only those tools. It refuses when a read in full is due.
|
|
110
|
+
|
|
111
|
+
Each read that ends also records, in the refresh log, whether it brought anything new (`change`: first, same or changed) and whether it read in full or asked first (`how`). PMOS measures this on the facts it stored, such as each event's time and title or each ticket's status, and not on the words Claude wrote. Nothing on the pages shows it yet; it measures how often each source really changes.
|
|
112
|
+
|
|
100
113
|
## Where you see it
|
|
101
114
|
|
|
102
115
|
Each page shows a short line that says when each source was last read, for example **Initiatives read 08:02 · Calendar read 07:15 · Jira status read 06:31**. On a screen wider than 600 pixels, the line is folded into one dot next to the date. The dot is amber and says how many sources are not read, for example **2 sources not read**, or it says **Sources read**. Press the dot to show the full line, and press it again to fold it. The line never says that the data is up to date, because the agents read these sources on a schedule and not live.
|
package/workspace/guide/home.md
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
type: Guide
|
|
3
3
|
title: "Home: your list, the chat and the Viewer"
|
|
4
|
-
description: "Home: the list grouped by product, the Viewer, the place menu, Your day
|
|
4
|
+
description: "Home: the list grouped by product, the Viewer, the place menu, Your day as the Good morning page, Search, and the initiative, meeting, report, Board and Insights features designed after it."
|
|
5
5
|
timestamp: 2026-11-04
|
|
6
6
|
---
|
|
7
7
|
|
|
@@ -15,13 +15,19 @@ Home, the Board, Insights and the Viewer use one typeface, Plus Jakarta Sans, wi
|
|
|
15
15
|
|
|
16
16
|
- The top line has **Good morning**, the product picker, the filter icon (on a desktop) and **New**. When the list is narrow, the icons move to a second line, so the greeting is never cut. The line under it says how many items are yours, for example "4 are yours".
|
|
17
17
|
- Press **Good morning** to open **Your day** in the Viewer. This is the same on a computer and on a phone. To open the calendar, press the calendar icon in Your day's header. A program's milestone changes that wait on you are the first line of the program's card.
|
|
18
|
-
- A blue dot after **Good morning** means that something is new for you. It is
|
|
19
|
-
- Your day
|
|
18
|
+
- A blue dot after **Good morning** means that something is new for you. It is under **Since yesterday** in Your day.
|
|
19
|
+
- Your day is the **Good morning** page. It shows the date and greeting, then the quarter, then two columns. On a computer it opens wide.
|
|
20
|
+
- **The quarter.** One bar with all goals of the products Home reads: reached, on track, still reading, at risk and will miss, each with its count. A black tick marks your line, for example "line 18". One sentence says how many goals are on track or better, and one line says why. **By product** opens Intelligence. With no goals, there is no bar. With no line, there is no tick, and Claude can propose a line with ✦: press ✓ to keep it, or ✕ to not set one this quarter. A product that could not be read is named and is not counted.
|
|
21
|
+
- **The left column.** Claude's lead, with one line of what Claude did for you. **Your call**: the one decision that needs you, and what Yes does when that is known. **Your move**: the top 3 items of the ranked list, each with the goal it moves and its due day (orange only when late). Then one line: **N more in Your move**, **N drafted for you** and **N can wait**. Press one to open its fold under the page. **Since yesterday**: up to 3 new items, then **New for you · N** to see all of them. ✓✓ marks all of them seen.
|
|
22
|
+
- **The right column.** Today's agenda, not to scale: a line at the time now, each meeting with its prep note, ✦ picks in free time, and "3 h free" for a long free stretch. The meeting where your call is decided has an orange edge. Under it, **Notes since yesterday**: meeting notes with their main lines, and recordings with no initiative. When Claude finds the initiative a recording belongs to, press the link icon to link it.
|
|
23
|
+
- **In the hour before a meeting**, the meeting's prep leads: what to agree, the points, and the record icon. The quarter shows only when it moved since the morning. Past meetings fade, with their notes under them.
|
|
24
|
+
- **On a phone or in a narrow Viewer**, the page is one column: the quarter, the lead, your call, Your move, the agenda, then Since yesterday.
|
|
25
|
+
- Under the page, the folds stay: the rest of **Your move**, **Drafted for you**, **Can wait**, **Now** (on a phone) and **This week** (the Weekly review).
|
|
20
26
|
- **Drafted for you** lists what Claude drafted today and the weekly update. Press a row to open it: a finished draft opens what Claude wrote, and the weekly update opens the update.
|
|
21
27
|
- Your day does not show the meeting on now or the next meeting. Home's meeting line shows them. On a phone, the **Now** card does not show while a meeting is in progress.
|
|
22
28
|
- When a conversation in Mentions waits on your answer, Your day names the oldest one under its first line: who asked, where, how many more wait, and what they asked. Press its icon to open that conversation in Mentions.
|
|
23
|
-
- **
|
|
24
|
-
- After 17:00, Your day is the end of the day.
|
|
29
|
+
- **Since yesterday** shows only when something is new: tasks given to you, and work that finished while you were away. It shows the 3 newest items, then **New for you · N**. Press an item to open it in the Viewer. Press **New for you · N** to see all of them. Press ✓✓ in its header to mark all of them seen. An item leaves when you open it or mark it seen. Mentions are not here: **Mentions** shows each one once.
|
|
30
|
+
- After 17:00, Your day is the end of the day. The quarter says how it moved since the morning. **Today made possible** lists what moved today, and **Still yours** lists what is left. The right column shows tomorrow's meetings.
|
|
25
31
|
- A **program** comes first, above the products. Its header shows the program icon, its name, the next milestone (◆ and the date) and how many of its initiatives are ready for that milestone. Inside it, the program's own tasks come first, then its initiatives under a small heading for each product. Each initiative shows once. Press the program's name to open the program in the Viewer. The chat then talks about the program. Press the chevron to close or open the group.
|
|
26
32
|
- The **product picker** is the chip on the top line. It shows the tiles of the ticked products, overlapped, with **+N** after 3, or **All** when every product is ticked. It shows even with one product. A git worktree of a repository is not a product: it does not appear in the list. Its repository stands for it. Hold the pointer on it to read the names. Press it to open the list: **All products**, then each product with its tile, its name and one line (for example "3 initiatives · 1 of 2 goals"), then **Add a product**. Press a product to tick or untick it; the list stays open, and the last ticked product stays ticked. The pick applies when the list closes (Escape, a press outside, or the chip again). On a phone the list is a sheet at the bottom. The pick is one saved setting (`ws.briefing.include`) that Home, the Board and Insights share, so a product that you untick on one page goes from all three. With **All** ticked, a product that you add later is ticked too. The **Product** row in Settings opens the same list.
|
|
27
33
|
- A program with no open initiative yet still shows, with "No initiatives yet" or "No open initiatives". A program shows only when it holds work of a ticked product. Home reads again when you come back to its tab, so a program made on the Board shows at once.
|
|
@@ -14,12 +14,12 @@ When you step away from PMOS, Claude can use the idle time to make prototypes an
|
|
|
14
14
|
A result for one initiative waits under that initiative's blue ✦, in one of three groups:
|
|
15
15
|
|
|
16
16
|
- **Claude prototyped it.** A first round of 2 or 3 different ways to do it, as thumbnails. Press a thumbnail to open it in the compare view.
|
|
17
|
-
- **Claude improved it.** A new round of one prototype. It says what changed, usually one thing, and where the change came from,
|
|
17
|
+
- **Claude improved it.** A new round of one prototype. It says what changed, usually one thing, and where the change came from: your ✕ reason, a grill finding or a scan finding.
|
|
18
18
|
- **Claude scanned for it.** A finding to attach as evidence, with the pages Claude read.
|
|
19
19
|
|
|
20
20
|
✓ keeps it as one of the initiative's documents. ✕ asks why first. Claude learns from the reason, and you can leave it empty. Press ✕ again to drop it. Undo in the toast takes a ✓ back.
|
|
21
21
|
|
|
22
|
-
A result that fits no initiative waits in **Intelligence › Lab**.
|
|
22
|
+
A result that fits no initiative waits in **Intelligence › Lab**. ✓ keeps the finding.
|
|
23
23
|
|
|
24
24
|
## The compare view
|
|
25
25
|
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
type: Guide
|
|
3
3
|
title: "The lifecycle: six stages and two milestones"
|
|
4
4
|
description: "The eight steps every initiative goes through, what each step makes, which steps each lane uses, and how the workspace knows where an initiative is."
|
|
5
|
-
timestamp: 2026-11-
|
|
5
|
+
timestamp: 2026-11-04
|
|
6
6
|
---
|
|
7
7
|
|
|
8
8
|
# The lifecycle: six stages and two milestones
|
|
@@ -35,9 +35,22 @@ A step that a lane does not use shows as skipped.
|
|
|
35
35
|
| content | Discover, Plan, Build, Deliver |
|
|
36
36
|
| prototype | Triage, Discover, Evaluate |
|
|
37
37
|
|
|
38
|
-
##
|
|
38
|
+
## One stage on every page
|
|
39
39
|
|
|
40
|
-
|
|
40
|
+
Every page shows the same stage chip: the Board row, the Timeline, the initiative page, Documents, the chat and the program page. The workspace reads the stage from these sources, in this order:
|
|
41
|
+
|
|
42
|
+
1. Your word. A lifecycle line (Completed shows Shipped, On hold, Cancelled), or a move on the Board that is newer than the last Jira read.
|
|
43
|
+
2. The linked Jira epic. Its status names the stage (Design Discovery shows Discover, In progress shows Build, Done shows Deliver, or Monitor after your sign-off). If the epic status names no stage, its tickets do: some started shows Build, all done shows Deliver.
|
|
44
|
+
3. Plan items with dates. A spec-agreed initiative with dated plan items shows Prioritize.
|
|
45
|
+
4. The spec files, as described below.
|
|
46
|
+
|
|
47
|
+
Hover the chip to see what set the stage and when Jira was last read. With no word from you and no Jira, the spec files decide.
|
|
48
|
+
|
|
49
|
+
The spec ladder (PRD, rubric, contract, review) shows as the gate line under the stage card. The CI Initiative Gate still reads the spec files. A task group shows a tick only when all of its tasks are done.
|
|
50
|
+
|
|
51
|
+
## How the spec files give the step
|
|
52
|
+
|
|
53
|
+
When no word and no Jira set the stage, the workspace reads it from the records:
|
|
41
54
|
|
|
42
55
|
- Triage, Discover, Plan, Build and Evaluate come from the workflow engine (`node scripts/workflow-state.js`): the PRD, the rubric and contract, the build, and the evaluation.
|
|
43
56
|
- An idea or a hypothesis on the initiative also counts for Discover.
|
|
@@ -20,6 +20,7 @@ The button is not on a narrow screen (720 px or less) and not on the All product
|
|
|
20
20
|
1. **Set the host.** The first time, the popover asks for the address of the board host. Ask the person who runs it. Write it as `https://boards.example.com`. The **Change** button on the form sets it again. If the computer has the `PMOS_BOARDS_HOST` variable, the variable is used.
|
|
21
21
|
2. **What to share.** The product of this board is picked. Your other products and your programs are chips under **Products** and **Programs**. A program chip names the products it reaches. Press a chip to add it. Press **Initiative** to pick one initiative of this board. Press a picked chip again to remove it. **Publish** stays off while nothing is picked.
|
|
22
22
|
- **Several picks are one link.** The reader sees one tab for each pick, in the order you picked them. A program tab opens the program's page with all its products. One pick shows no tabs.
|
|
23
|
+
- **A program with nothing on a product.** When a program you picked holds nothing on one of its products (its initiative there is done or gone), the copy leaves that program out of that product only. Your other picks on that product stay. If a program holds nothing on any of its products, Publish says so.
|
|
23
24
|
- **The name.** With two or more picks, the link's name is made from them: three names, then "+ N more". Press the pencil to change it. **Republish** keeps every pick and the name.
|
|
24
25
|
- **The size.** The whole link can be at most 2 MB. When your picks are more, PMOS says so and sends nothing. Pick less.
|
|
25
26
|
3. **Team.** Type the name of a team, or leave it empty. The host tells you when there is no team with that name.
|
|
@@ -79,6 +80,7 @@ The tab is not in the read-only Board. A reader sees no Shared tab.
|
|
|
79
80
|
- The span picker, the Deliveries lane, and the folds of a program and a product.
|
|
80
81
|
- One line above the Board. It names the selection, the date of the copy, who shared it and when the link ends. It ends with **Open in my PMOS** and **Get PMOS**.
|
|
81
82
|
- One tab for each pick, when the link holds two or more products or programs.
|
|
83
|
+
- On a program's page, the initiatives of its other products that the copy holds.
|
|
82
84
|
- A viewer for each initiative. Press the name of an initiative to open it, on the stage track or on the Timeline. The viewer shows the stage card, About and Tasks. Tasks show for every initiative, also when a stage has a note such as "The rest, by work package". Tasks show as a List or as a Timeline, grouped by stage, owner or status.
|
|
83
85
|
- The panel divider and the panel layout: full screen, split or slide over.
|
|
84
86
|
|
package/workspace/guide/today.md
CHANGED
|
@@ -2,15 +2,23 @@
|
|
|
2
2
|
type: Guide
|
|
3
3
|
title: "What waits for you, and pmos today"
|
|
4
4
|
description: "Where the workspace shows what waits for you (Your day in Home) and how pmos today prints the same kind of list from a terminal."
|
|
5
|
-
timestamp: 2026-11-
|
|
5
|
+
timestamp: 2026-11-04
|
|
6
6
|
---
|
|
7
7
|
|
|
8
8
|
# What waits for you, and pmos today
|
|
9
9
|
|
|
10
10
|
In the workspace, what waits for you is in **Your day** on Home. Press **Good morning** at the top of Home's list to open it in the Viewer.
|
|
11
11
|
|
|
12
|
-
- **Your move**
|
|
13
|
-
|
|
12
|
+
- **Your move** is one ranked list of everything Claude proposes (✦) that waits on you, with its count. Each row shows how long it has waited. The order is:
|
|
13
|
+
1. Outcome checks past their date. When Claude could read the Jira tickets, it drafts Keep or Iterate, and ✓ records that verdict. When it could not read enough, ✎ opens Intelligence. Claude never drafts Stop.
|
|
14
|
+
2. Grill findings on work that shipped or is late.
|
|
15
|
+
3. Milestone changes per program, as one row. ✓ confirms all of them, and ✎ lets you pick.
|
|
16
|
+
4. Grill findings on work ahead.
|
|
17
|
+
5. The first key result with no reading, and the source it waits on.
|
|
18
|
+
6. The other proposals, one row per initiative. A row older than two weeks folds under **Older than two weeks**.
|
|
19
|
+
- In Your move, findings of one kind on one initiative are one row, with the others counted ("2 more findings like it"). ✕ drops a finding.
|
|
20
|
+
- **New for you** shows what is new since you last looked. When there are two or more tasks given to you, they are one row. Work that finished while you were away is also listed.
|
|
21
|
+
- When you have no meeting today, Your day shows no meeting line and no offer to prepare.
|
|
14
22
|
- **Drafted for you** lists what Claude drafted today.
|
|
15
23
|
- **This week** opens the weekly review.
|
|
16
24
|
|
|
@@ -17,7 +17,8 @@
|
|
|
17
17
|
* 3 driver the Initiative Driver
|
|
18
18
|
* 4 deep the deep drafts: core documents, Your impact, metric drafts and reads, proposals, grill, the report finder, the
|
|
19
19
|
* report design and structure checks, milestone reviews, the forecast
|
|
20
|
-
* 5 idle the idle lab and the slow reads: the Horizon scan (its daily run waits for the first idle stretch of the day)
|
|
20
|
+
* 5 idle the idle lab and the slow reads: the Horizon scan (its daily run waits for the first idle stretch of the day), then the idle
|
|
21
|
+
* lab (lib/idle-lab-engine.js: prototypes and scans for the PM's initiatives)
|
|
21
22
|
*
|
|
22
23
|
* THE CHECKS (made once per tick, for every job):
|
|
23
24
|
* off switch lib/ai-guard.js off(job): PMOS_AI=off, PMOS_AI_<JOB>=off, Settings ai.on / ai.off (`pmos ai off [job]`). A job with
|
|
@@ -77,6 +78,7 @@ const JOBS = Object.freeze([
|
|
|
77
78
|
{ id: 'report-design', step: 4, label: 'Report design' },
|
|
78
79
|
{ id: 'report-structure', step: 4, label: 'Report structure' },
|
|
79
80
|
{ id: 'scan', step: 5, label: 'Horizon scan' },
|
|
81
|
+
{ id: 'idle-lab', step: 5, label: 'Idle lab' },
|
|
80
82
|
]);
|
|
81
83
|
const BY_ID = new Map(JOBS.map((j) => [j.id, j]));
|
|
82
84
|
const LAST_HOUR_MS = 60 * 60 * 1000;
|
|
@@ -122,18 +124,20 @@ function holderOf(sessions, initiative, { except = null } = {}) {
|
|
|
122
124
|
}
|
|
123
125
|
return null;
|
|
124
126
|
}
|
|
125
|
-
/** The initiative an origin names: drive:initiative:<id>, grill:<ws>:<id>:<run>, propose:<ws>:<id>:<run>. */
|
|
127
|
+
/** The initiative an origin names: drive:initiative:<id>, grill:<ws>:<id>:<run>, propose:<ws>:<id>:<run>, idle-lab-proto|idle-lab-scan:<ws>:<id|->:<run>. */
|
|
126
128
|
function initiativeOfOrigin(origin) {
|
|
127
129
|
const p = String(origin || '').split(':');
|
|
128
130
|
if (p[0] === 'drive' && p[1] === 'initiative') return p.slice(2).join(':') || null;
|
|
129
131
|
if ((p[0] === 'grill' || p[0] === 'propose') && p.length >= 4) return p[2] || null;
|
|
132
|
+
if ((p[0] === 'idle-lab-proto' || p[0] === 'idle-lab-scan') && p.length >= 4) return p[2] && p[2] !== '-' ? p[2] : null;
|
|
130
133
|
return null;
|
|
131
134
|
}
|
|
132
135
|
|
|
133
136
|
/* origin prefix → queue job. Origins not listed (a refresh source, a schedule, next-step) keep their prefix as the job name. */
|
|
134
137
|
const ORIGIN_JOB = Object.freeze({ drive: 'driver', grill: 'grill', propose: 'propose', 'metric-read': 'metric-reads', 'metric-draft': 'metric-drafts',
|
|
135
138
|
impact: 'impact', coredoc: 'coredocs', 'core-docs': 'coredocs', 'scan-web': 'scan', 'scan-repo': 'scan', 'scan-suggest': 'scan',
|
|
136
|
-
'scan-research-web': 'scan', 'scan-research-repo': 'scan', 'report-find': 'finder', 'ms-review': 'milestones', 'next-step': 'prepare'
|
|
139
|
+
'scan-research-web': 'scan', 'scan-research-repo': 'scan', 'report-find': 'finder', 'ms-review': 'milestones', 'next-step': 'prepare',
|
|
140
|
+
'idle-lab-proto': 'idle-lab', 'idle-lab-scan': 'idle-lab' });
|
|
137
141
|
function jobOfOrigin(origin) {
|
|
138
142
|
const o = String(origin || '');
|
|
139
143
|
if (!o || /^chat:/.test(o)) return null;
|
|
@@ -244,8 +244,11 @@ function wfFields(r) {
|
|
|
244
244
|
const wfMap = mapFields(r.wfMap);
|
|
245
245
|
const wfSwitch = r.wfSwitch && typeof r.wfSwitch.batch === 'string' ? { batch: r.wfSwitch.batch, at: r.wfSwitch.at || null, from: r.wfSwitch.from || null } : null;
|
|
246
246
|
return { wf, wfStage: stageFields(r.wfStage), wfStages: Array.isArray(r.wfStages) ? r.wfStages.map(stageFields).filter(Boolean).slice(0, 40) : null, ended,
|
|
247
|
-
...(wfMap ? { wfMap } : {}), ...(wfSwitch ? { wfSwitch } : {}) };
|
|
247
|
+
...(wfMap ? { wfMap } : {}), ...(wfSwitch ? { wfSwitch } : {}), ...(r.oneStage ? { oneStage: oneFields(r.oneStage) } : {}) };
|
|
248
248
|
}
|
|
249
|
+
/** W1: the one stage as the routes give it (lib/one-stage.js stageOf): the chip (public/pm/stage-chip.js) draws it on every surface. */
|
|
250
|
+
const oneFields = (o) => (o && typeof o === 'object' && o.stage ? { stage: String(o.stage), step: String(o.step || ''), label: clip(o.label || '', 40),
|
|
251
|
+
setBy: ['pm', 'jira', 'plan', 'files'].includes(o.setBy) ? o.setBy : 'files', source: clip(o.source || '', 120), readAt: o.readAt || null } : null);
|
|
249
252
|
/** A stage map as the row carries it: { old key: stage key }, short strings only (a key is never cut: a cut key matches nothing), at most 60
|
|
250
253
|
* keys; null when empty. */
|
|
251
254
|
function mapFields(m) {
|
|
@@ -60,16 +60,28 @@ function labelFrom(pack, tab) {
|
|
|
60
60
|
async function packOf(parts, o) {
|
|
61
61
|
const g = groupsOf(parts, o.programs, o.boards);
|
|
62
62
|
if (g.error) return { ok: false, status: 400, error: g.error };
|
|
63
|
-
const packs = new Map();
|
|
63
|
+
const packs = new Map(); const reached = new Map(); // program id -> the products it kept something on, in group order
|
|
64
64
|
for (const grp of g.groups) {
|
|
65
|
-
|
|
65
|
+
let sel = grp.select.split(','); let r = await o.make(grp);
|
|
66
|
+
// a program with nothing on this product (its member here is done or gone) is dropped from this product only; the other picks here still go
|
|
67
|
+
while (!r.ok && r.status === 400) {
|
|
68
|
+
const m = /^"([^"]+)" is not on this board\./.exec(String(r.error || ''));
|
|
69
|
+
const drop = m && sel.find((s) => s === 'program:' + m[1]);
|
|
70
|
+
if (!drop || sel.length < 2) break;
|
|
71
|
+
sel = sel.filter((s) => s !== drop); r = await o.make(Object.assign({}, grp, { select: sel.join(',') }));
|
|
72
|
+
}
|
|
66
73
|
if (!r.ok) {
|
|
67
74
|
// a product a program only reaches, with nothing of the program on it now: left out, the program's other products still go
|
|
68
75
|
if (r.status === 400 && /not on this board/.test(r.error) && !parts.some((p) => p.ws === grp.ws)) continue;
|
|
69
76
|
return r;
|
|
70
77
|
}
|
|
71
78
|
packs.set(grp.ws, r.pack);
|
|
79
|
+
for (const s of sel) if (s.startsWith('program:')) { const id = s.slice(8); reached.set(id, (reached.get(id) || []).concat([grp.ws])); }
|
|
72
80
|
}
|
|
81
|
+
// a program picked must show: one with nothing on any of its products is said, never dropped in silence
|
|
82
|
+
for (const p of parts) if (p.kind === 'program' && !reached.has(p.id)) { const t = g.tabs.find((x) => x.program === p.id); return { ok: false, status: 400, error: ((t && t.label) || p.id) + ' has nothing on its products to share yet.' }; }
|
|
83
|
+
// a program's tab opens on its home product, or on the first product it kept something on when it has nothing at home
|
|
84
|
+
for (const t of g.tabs) if (t.program && !reached.get(t.program).includes(t.ws)) { const ws = reached.get(t.program)[0]; t.ws = ws; t.board = ((o.boards || []).find((b) => b && b.ws === ws) || {}).id || ws; }
|
|
73
85
|
if (!packs.size) return { ok: false, status: 400, error: 'Nothing in these picks can be shared yet.' };
|
|
74
86
|
// one tab per pick; an initiative joins its product's tab when that product is picked too, and initiatives of one product share a tab
|
|
75
87
|
const tabs = []; const seen = new Map();
|