create-pmos 0.130.0 → 0.131.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 +1 -1
- 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/c3-one-home-test.js +4 -2
- package/workspace/c3-work-test.js +200 -0
- package/workspace/fixtures/one-home-baseline.json +0 -91
- package/workspace/guide/console-calendar.md +65 -0
- package/workspace/guide/index.md +1 -0
- package/workspace/guide/my-work.md +76 -1
- package/workspace/lib/calendar-layers.js +372 -0
- package/workspace/lib/pm-items.js +71 -6
- package/workspace/lib/report-needs.js +1 -1
- package/workspace/lib/routes-calendar-views.js +112 -3
- package/workspace/lib/routes-pm-items.js +123 -13
- package/workspace/lib/work-focus.js +106 -0
- package/workspace/package-lock.json +2 -2
- package/workspace/package.json +1 -1
- package/workspace/public/pm/c3-calendar.js +392 -0
- package/workspace/public/pm/c3-demo-cal4.js +114 -0
- package/workspace/public/pm/c3-demo-data.js +79 -77
- package/workspace/public/pm/c3-demo-misc2.js +4 -16
- package/workspace/public/pm/c3-demo-work-ix.js +19 -67
- package/workspace/public/pm/c3-demo.js +10 -3
- package/workspace/public/pm/c3-shell.js +1 -1
- package/workspace/public/pm/calendar-views.js +10 -3
- package/workspace/public/pm/components.css +1 -0
- package/workspace/public/pm/console3.css +155 -0
- package/workspace/public/pm/pm-work-view.js +364 -172
- package/workspace/public/pm/work-place.js +58 -0
- package/workspace/test-files.json +2 -0
- package/workspace/test-lists/calendar-layers.json +5 -0
- package/workspace/test-lists/calendar-time-page.json +5 -0
- package/workspace/test-lists/console3-work-page.json +9 -0
- package/workspace/public/pm/c3-demo-work2.js +0 -13
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
/* pm/work-place.js — the Work page's placement rule, as the client needs it (initiative console3-work-page, PRD R2, R5, R7).
|
|
2
|
+
*
|
|
3
|
+
* The SERVER places every item (lib/pm-items.js workPlacement) and answers GET /api/pm-items with `work`, `review` and `counts`.
|
|
4
|
+
* The client never copies an item from one view to another. It uses this copy of the rule for two things only:
|
|
5
|
+
* 1. the capture line's preview chip, which says where a new line lands before it is saved;
|
|
6
|
+
* 2. demo mode (/c3.html?demo=1), where nothing reaches the server, so the fixture and the in-memory overlay are placed here.
|
|
7
|
+
* The rule, in order: parked is Someday; waiting on someone is Waiting; a "not before" (defer) date after today is Upcoming;
|
|
8
|
+
* flagged is Today; due today or earlier is Today; a later due date is Upcoming; no date is Inbox. Dates are YYYY-MM-DD strings.
|
|
9
|
+
* Pure: no DOM, no fetch. */
|
|
10
|
+
|
|
11
|
+
export const VIEWS = Object.freeze(['inbox', 'today', 'upcoming', 'waiting', 'someday']);
|
|
12
|
+
export const REVIEW_DAYS = 7;
|
|
13
|
+
|
|
14
|
+
const day = (s) => (s ? String(s).slice(0, 10) : '');
|
|
15
|
+
export function addIso(s, n) { const d = new Date(day(s) + 'T00:00:00Z'); d.setUTCDate(d.getUTCDate() + n); return d.toISOString().slice(0, 10); }
|
|
16
|
+
export function daysBetween(a, b) { return Math.round((Date.parse(day(b) + 'T00:00:00Z') - Date.parse(day(a) + 'T00:00:00Z')) / 86400000); }
|
|
17
|
+
|
|
18
|
+
/** The view an open item belongs in. */
|
|
19
|
+
export function workPlace(item, today) {
|
|
20
|
+
const i = item || {};
|
|
21
|
+
if (i.parked) return 'someday';
|
|
22
|
+
if (i.waiting_on) return 'waiting';
|
|
23
|
+
if (i.defer && day(i.defer) > today) return 'upcoming';
|
|
24
|
+
if (i.flagged) return 'today';
|
|
25
|
+
if (i.due && day(i.due) <= today) return 'today';
|
|
26
|
+
if (i.due) return 'upcoming';
|
|
27
|
+
return 'inbox';
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
/** The day an Upcoming item arrives: its "not before" date when that is still ahead, else its due date. */
|
|
31
|
+
export function arrives(item, today) { return item.defer && day(item.defer) > today ? day(item.defer) : day(item.due); }
|
|
32
|
+
|
|
33
|
+
/** The days since the item was last touched (any event), from touched_at, else created_at. */
|
|
34
|
+
export function untouchedDays(item, today) { const t = day(item.touched_at || item.created_at); return t ? daysBetween(t, today) : 0; }
|
|
35
|
+
|
|
36
|
+
const byStr = (a, b) => (a < b ? -1 : a > b ? 1 : 0);
|
|
37
|
+
/** Each view in the order the PRD's contract gives: Today overdue first, then flagged, then by due; Upcoming by arrival; Inbox newest first. */
|
|
38
|
+
export function sortView(view, list, today) {
|
|
39
|
+
const l = list.slice();
|
|
40
|
+
if (view === 'today') {
|
|
41
|
+
const rank = (i) => (i.due && day(i.due) < today ? 0 : i.flagged ? 1 : 2);
|
|
42
|
+
l.sort((a, b) => rank(a) - rank(b) || byStr(day(a.due) || '9999', day(b.due) || '9999') || byStr(String(a.time || ''), String(b.time || '')));
|
|
43
|
+
} else if (view === 'upcoming') l.sort((a, b) => byStr(arrives(a, today), arrives(b, today)));
|
|
44
|
+
else if (view === 'inbox') l.sort((a, b) => byStr(String(b.created_at || ''), String(a.created_at || '')));
|
|
45
|
+
return l;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
/** { work, review, counts } for a set of items (done ones are left out), as the server's answer has them. */
|
|
49
|
+
export function buildWork(items, today, reviewDays = REVIEW_DAYS) {
|
|
50
|
+
const work = Object.fromEntries(VIEWS.map((v) => [v, []]));
|
|
51
|
+
const open = (items || []).filter((i) => i && !i.done);
|
|
52
|
+
open.forEach((i) => work[workPlace(i, today)].push(i));
|
|
53
|
+
VIEWS.forEach((v) => { work[v] = sortView(v, work[v], today); });
|
|
54
|
+
const review = open.filter((i) => ['inbox', 'someday', 'waiting'].includes(workPlace(i, today)) && untouchedDays(i, today) >= reviewDays)
|
|
55
|
+
.sort((a, b) => untouchedDays(b, today) - untouchedDays(a, today));
|
|
56
|
+
const counts = { ...Object.fromEntries(VIEWS.map((v) => [v, work[v].length])), review: review.length };
|
|
57
|
+
return { work, review, counts };
|
|
58
|
+
}
|
|
@@ -25,6 +25,7 @@
|
|
|
25
25
|
"pm-items.test.js",
|
|
26
26
|
"jobs-to-be-done.test.js",
|
|
27
27
|
"pm-items-routes.test.js",
|
|
28
|
+
"work-focus.test.js",
|
|
28
29
|
"brief-page.test.js",
|
|
29
30
|
"item-steps.test.js",
|
|
30
31
|
"status-facts-panel.test.js",
|
|
@@ -147,6 +148,7 @@
|
|
|
147
148
|
"pm-items.test.js": 1,
|
|
148
149
|
"jobs-to-be-done.test.js": 1,
|
|
149
150
|
"pm-items-routes.test.js": 1,
|
|
151
|
+
"work-focus.test.js": 1,
|
|
150
152
|
"brief-page.test.js": 1,
|
|
151
153
|
"pm-brief-page-test.js": 30,
|
|
152
154
|
"item-steps.test.js": 1,
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
/* pm/c3-demo-work2.js — demo-only fixtures of the Work tab's Jobs card (/c3.html?demo=1). Sets window.__c3work2, which pm-work-view.js reads in demo mode only.
|
|
2
|
-
* jobAll: for each job, the items the mockup lists in its case file under "All N items, across every list" (console3.html c3jall, line 4653),
|
|
3
|
-
* grouped by list in the order triage, today, week, waiting, later, done. Each group is [list label, [titles], struck-through?]. The titles are the
|
|
4
|
-
* mockup's own S.items (line 1070); the demo list data holds a few more items under job 1, so the count shown here is the mockup's. */
|
|
5
|
-
window.__c3work2 = {
|
|
6
|
-
jobAll: {
|
|
7
|
-
j1: [['Triage', ['Assign owners to 2 unowned workshop actions', 'Approve pricing-page copy before handoff', 'Confirm the growth assumption in the Q4 forecast']],
|
|
8
|
-
['Today', ['Cut Checkout v2 to 3 core flows to hold 24 Oct?']], ['Waiting', ['Payments sandbox keys', 'Annual-plan label']], ['Done', ['Send revised PRD to Dara'], true]],
|
|
9
|
-
j2: [['Triage', ['Confirm the 1 Oct numbers before the 10:30 update']]],
|
|
10
|
-
j3: [['Triage', ['Review the 13:00 interview guide', 'Pick interview slots with 3 customers', 'Accept the 15 Oct interview invite']], ['Week', ['Share returns insights with sales']]],
|
|
11
|
-
j4: [['Week', ['Confirm the SSO date to Marta']]],
|
|
12
|
-
},
|
|
13
|
-
};
|