@bongos/core 1.20.47 → 1.20.49
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/.bongos-core.json +108 -73
- package/docs/copy-inventory.md +200 -184
- package/docs/copy-registry.json +364 -220
- package/docs/module-api-changelog.md +4 -0
- package/docs/page-inventory.json +11 -4
- package/docs/page-readings.json +411 -386
- package/modules/hall-ui/public/atlas.html +1 -1
- package/modules/hall-ui/public/blockers.html +1 -1
- package/modules/hall-ui/public/board-room.html +1 -1
- package/modules/hall-ui/public/collab.html +1 -1
- package/modules/hall-ui/public/commands.html +1 -1
- package/modules/hall-ui/public/copy-desk.html +1 -1
- package/modules/hall-ui/public/criterion-uat-ui.js +280 -0
- package/modules/hall-ui/public/deploy.html +1 -1
- package/modules/hall-ui/public/diagrams.html +1 -1
- package/modules/hall-ui/public/drachmae.html +1 -1
- package/modules/hall-ui/public/fleet.html +1 -1
- package/modules/hall-ui/public/gate.html +1 -1
- package/modules/hall-ui/public/goal-map.html +5 -3
- package/modules/hall-ui/public/goals-page.js +23 -44
- package/modules/hall-ui/public/goals-render.js +24 -15
- package/modules/hall-ui/public/goals.css +45 -0
- package/modules/hall-ui/public/goals.html +6 -3
- package/modules/hall-ui/public/goals.states.json +38 -0
- package/modules/hall-ui/public/government.html +1 -1
- package/modules/hall-ui/public/hall-render.js +3 -0
- package/modules/hall-ui/public/idea.html +1 -1
- package/modules/hall-ui/public/ideas.html +1 -1
- package/modules/hall-ui/public/index.html +1 -1
- package/modules/hall-ui/public/modules.html +1 -1
- package/modules/hall-ui/public/primer.html +1 -1
- package/modules/hall-ui/public/profile.html +1 -1
- package/modules/hall-ui/public/project-settings.html +1 -1
- package/modules/hall-ui/public/ranks.html +1 -1
- package/modules/hall-ui/public/roadmap.html +1 -1
- package/modules/hall-ui/public/roster.html +1 -1
- package/modules/hall-ui/public/sessions.html +1 -1
- package/modules/hall-ui/public/settings.html +1 -1
- package/modules/hall-ui/public/shell.js +82 -1
- package/modules/hall-ui/public/sky-data.js +9 -1
- package/modules/hall-ui/public/sky-interaction.js +1 -1
- package/modules/hall-ui/public/sky-panel.js +1 -1
- package/modules/hall-ui/public/studio.html +1 -1
- package/modules/hall-ui/public/style.css +36 -0
- package/modules/hall-ui/public/task.html +1 -1
- package/modules/hall-ui/public/thinking.html +6 -4
- package/modules/hall-ui/public/tweak-editor.html +1 -1
- package/modules/hall-ui/public/watch.html +1 -1
- package/modules/hall-ui/public/work-founding.states.json +39 -0
- package/modules/hall-ui/public/work.html +1 -1
- package/modules/hall-ui/records/founding-mode.md +31 -0
- package/modules/lifecycle/done-when.js +3 -1
- package/modules/lifecycle/sky.js +23 -8
- package/modules/onboarding/founding-mode.js +185 -0
- package/modules/onboarding/port.js +7 -0
- package/modules/ui-design/kit/fixtures/me-founding.json +24 -0
- package/modules/ui-design/kit/serve.js +3 -1
- package/package-lock.json +2 -2
- package/package.json +1 -1
- package/release-notes.json +12 -0
- package/scripts/hall-preview/server.js +2 -0
- package/src/bongos/routes/me.js +18 -1
- package/src/module-api.js +1 -1
- package/tests/claim_action.mjs +6 -1
- package/tests/criterion_uat_ui.mjs +113 -0
- package/tests/founding_mode.mjs +294 -0
- package/tests/goal_criterion_confirm_ui.mjs +188 -91
- package/tests/goal_map_page.mjs +2 -1
- package/tests/hall_sky.mjs +16 -0
- package/tests/hall_tweak_editor.mjs +1 -1
- package/tests/helpers.mjs +3 -1
- package/tests/nav_permission_atoms.mjs +1 -1
- package/tests/sky_read.mjs +7 -1
|
@@ -178,6 +178,51 @@
|
|
|
178
178
|
white-space: nowrap; padding: 2px 8px; border-radius: var(--radius-pill);
|
|
179
179
|
background: var(--warn-weak); color: var(--warn); font-size: 10.5px; font-weight: 600;
|
|
180
180
|
}
|
|
181
|
+
/* task 1004402 (ADR 0351) — the UAT on a criterion. The state pill and the
|
|
182
|
+
Backend-only tag sit with the label; the panel spans the whole row under it.
|
|
183
|
+
Status tones reuse the hall's measured --ok / --warn pairs (DESIGN.md §Reuse):
|
|
184
|
+
awaiting reads as the warn state the "!" mark already uses, a UAT close as ok,
|
|
185
|
+
and the quieter closes (override, closed before UAT) in plain ink. */
|
|
186
|
+
.crit__badges { display: inline-flex; flex-wrap: wrap; gap: 4px; margin-left: 4px; vertical-align: 1px; }
|
|
187
|
+
.crit-state, .crit-tag {
|
|
188
|
+
white-space: nowrap; padding: 1px 7px; border-radius: var(--radius-pill);
|
|
189
|
+
font-size: 10.5px; font-weight: 600; line-height: 1.5;
|
|
190
|
+
background: var(--rule-soft); color: var(--ink-soft);
|
|
191
|
+
}
|
|
192
|
+
.crit-state--awaiting_uat { background: var(--warn-weak); color: var(--warn); }
|
|
193
|
+
.crit-state--satisfied_uat, .crit-state--satisfied_backend { background: var(--ok-weak); color: var(--ok); }
|
|
194
|
+
.crit-tag { background: transparent; border: var(--line) solid var(--rule); }
|
|
195
|
+
.crit__link {
|
|
196
|
+
cursor: pointer; white-space: nowrap; min-height: 24px; padding: 3px 6px; margin: 0 -6px;
|
|
197
|
+
border: 0; background: transparent; color: var(--ink-soft); font: inherit; font-size: 11.5px;
|
|
198
|
+
text-decoration: underline; text-underline-offset: 3px;
|
|
199
|
+
}
|
|
200
|
+
.crit__link:hover:not(:disabled) { color: var(--ink); }
|
|
201
|
+
.crit__link:disabled { opacity: .6; cursor: default; }
|
|
202
|
+
.uat-panel {
|
|
203
|
+
grid-column: 1 / -1; margin: 6px 0 4px 32px; padding: 12px 14px;
|
|
204
|
+
border-radius: var(--radius); background: color-mix(in srgb, var(--ink) 5%, var(--bg-card));
|
|
205
|
+
font-size: 12.5px; color: var(--ink-soft); display: flex; flex-direction: column; gap: 10px;
|
|
206
|
+
}
|
|
207
|
+
.uat-checks { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 4px; }
|
|
208
|
+
.uat-check { display: grid; grid-template-columns: 16px 64px minmax(0,1fr); gap: 6px; align-items: baseline; }
|
|
209
|
+
.uat-check__mark { color: var(--ink-faint); text-align: center; }
|
|
210
|
+
.uat-check--ok .uat-check__mark { color: var(--ok); font-weight: 700; }
|
|
211
|
+
.uat-check__label { font-weight: 600; color: var(--ink); }
|
|
212
|
+
.uat-video { width: 100%; max-width: 560px; border-radius: var(--radius); background: var(--ink); }
|
|
213
|
+
.uat-form { display: flex; flex-direction: column; gap: 8px; }
|
|
214
|
+
.uat-field { display: flex; flex-direction: column; gap: 4px; }
|
|
215
|
+
.uat-field input[type="file"] { min-height: 24px; font: inherit; font-size: 12px; }
|
|
216
|
+
.uat-field textarea {
|
|
217
|
+
font: inherit; font-size: 12.5px; padding: 6px 8px; border-radius: var(--radius);
|
|
218
|
+
border: var(--line) solid var(--rule); background: var(--bg-card); color: var(--ink); resize: vertical;
|
|
219
|
+
}
|
|
220
|
+
.uat-check-input { display: inline-flex; align-items: center; gap: 8px; min-height: 24px; cursor: pointer; }
|
|
221
|
+
.uat-check-input input { width: 16px; height: 16px; margin: 0; }
|
|
222
|
+
.uat-hint { margin: 0; }
|
|
223
|
+
.uat-error { margin: 0; color: var(--danger, var(--warn)); font-weight: 600; }
|
|
224
|
+
.uat-form .crit__confirm { align-self: flex-start; min-height: 32px; padding: 6px 14px; }
|
|
225
|
+
|
|
181
226
|
/* BV1.R79: per-criterion expand in the capped band — short label, full text on
|
|
182
227
|
click (matches the Roadmap page's .vbar__crit-d pattern). */
|
|
183
228
|
.crit-d { min-width: 0; }
|
|
@@ -230,7 +230,7 @@
|
|
|
230
230
|
|
|
231
231
|
<div id="toast" class="toast" role="status" aria-live="polite" data-visible="0"></div>
|
|
232
232
|
|
|
233
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
233
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
234
234
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
235
235
|
<script src="/builders/palette.js" defer></script>
|
|
236
236
|
<script src="/builders/dom-utils.js?v=2026-06-14-domutils"></script>
|
|
@@ -257,7 +257,10 @@
|
|
|
257
257
|
began — goals-lib took the pure helpers, this takes the view painters.
|
|
258
258
|
Loaded BEFORE goals-page.js, which calls window.OTBGoalsRender(ctx). -->
|
|
259
259
|
<script src="/builders/bulk-toolbar.js"></script>
|
|
260
|
-
|
|
261
|
-
|
|
260
|
+
<!-- task 1004402: the criterion UAT pills, panel and sign-off (ADR 0351). Loaded
|
|
261
|
+
BEFORE goals-render.js, which reads window.OTBCriterionUat at factory time. -->
|
|
262
|
+
<script src="/builders/criterion-uat-ui.js?v=2026-09-30-uat2"></script>
|
|
263
|
+
<script src="/builders/goals-render.js?v=2026-09-30-uat2"></script>
|
|
264
|
+
<script src="/builders/goals-page.js?v=2026-09-30-uat2"></script>
|
|
262
265
|
</body>
|
|
263
266
|
</html>
|
|
@@ -128,6 +128,44 @@
|
|
|
128
128
|
},
|
|
129
129
|
"out": {
|
|
130
130
|
"auth": false
|
|
131
|
+
},
|
|
132
|
+
"uat": {
|
|
133
|
+
"auth": true,
|
|
134
|
+
"url": "/builders/goals#/goal/1000111/completion",
|
|
135
|
+
"actions": [
|
|
136
|
+
[
|
|
137
|
+
"wait",
|
|
138
|
+
800
|
|
139
|
+
]
|
|
140
|
+
],
|
|
141
|
+
"expect": {
|
|
142
|
+
"visible": [
|
|
143
|
+
"#goal-completion-full"
|
|
144
|
+
]
|
|
145
|
+
}
|
|
146
|
+
},
|
|
147
|
+
"uat-panel": {
|
|
148
|
+
"auth": true,
|
|
149
|
+
"url": "/builders/goals#/goal/1000111/completion",
|
|
150
|
+
"actions": [
|
|
151
|
+
[
|
|
152
|
+
"wait",
|
|
153
|
+
800
|
|
154
|
+
],
|
|
155
|
+
[
|
|
156
|
+
"click",
|
|
157
|
+
"#goal-completion-full [data-uat-open=\"990001\"]"
|
|
158
|
+
],
|
|
159
|
+
[
|
|
160
|
+
"wait",
|
|
161
|
+
500
|
|
162
|
+
]
|
|
163
|
+
],
|
|
164
|
+
"expect": {
|
|
165
|
+
"visible": [
|
|
166
|
+
"#goal-completion-full .uat-form"
|
|
167
|
+
]
|
|
168
|
+
}
|
|
131
169
|
}
|
|
132
170
|
},
|
|
133
171
|
"reducedMotion": {
|
|
@@ -134,7 +134,7 @@
|
|
|
134
134
|
|
|
135
135
|
<div id="toast" class="toast" role="status" aria-live="polite" data-visible="0"></div>
|
|
136
136
|
|
|
137
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
137
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
138
138
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
139
139
|
<script src="/builders/palette.js" defer></script>
|
|
140
140
|
<script src="/builders/dom-utils.js?v=2026-06-16-gate"></script>
|
|
@@ -221,6 +221,9 @@
|
|
|
221
221
|
// same reason: the index is where a builder lands, so omitting it here
|
|
222
222
|
// would mean the badge appeared everywhere EXCEPT the page they open first.
|
|
223
223
|
needs: (ctx.lastMeState && ctx.lastMeState.needs) || null,
|
|
224
|
+
// task 1004422: project founding mode — passed here for the same reason as the
|
|
225
|
+
// three above, or the index would be the one page the band never appears on.
|
|
226
|
+
founding: (ctx.lastMeState && ctx.lastMeState.founding_mode) || null,
|
|
224
227
|
builder,
|
|
225
228
|
});
|
|
226
229
|
|
|
@@ -52,7 +52,7 @@
|
|
|
52
52
|
|
|
53
53
|
<div id="toast" class="toast" role="status" aria-live="polite" data-visible="0"></div>
|
|
54
54
|
|
|
55
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
55
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
56
56
|
<script src="/builders/palette.js" defer></script>
|
|
57
57
|
<script src="/builders/dom-utils.js?v=2026-06-23-contrib" defer></script>
|
|
58
58
|
<!-- task-detail.js still owns the #/idea/N and #/blocker/N overlay, so a ref
|
|
@@ -225,7 +225,7 @@
|
|
|
225
225
|
|
|
226
226
|
<div id="toast" class="toast" role="status" aria-live="polite" data-visible="0"></div>
|
|
227
227
|
|
|
228
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
228
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
229
229
|
<script src="/builders/palette.js" defer></script>
|
|
230
230
|
<script src="/builders/dom-utils.js?v=2026-06-23-contrib"></script>
|
|
231
231
|
<!-- task 1003069 (R08) — the quick-filing form's routed result links a task
|
|
@@ -106,7 +106,7 @@
|
|
|
106
106
|
<script src="/builders/brand-apply.js?v=2026-06-27-r75" defer></script>
|
|
107
107
|
<!-- The app shell (sidebar + top bar + view router). Dependency-free; loaded
|
|
108
108
|
BEFORE builders.js so the chrome ids exist when events are wired. -->
|
|
109
|
-
<script src="/builders/shell.js?v=2026-09-30-commands" defer></script>
|
|
109
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands" defer></script>
|
|
110
110
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
111
111
|
<script src="/builders/palette.js" defer></script>
|
|
112
112
|
<!-- task 2166: the shared component kit (window.OTBKit) — pager/ledger/rail.
|
|
@@ -101,7 +101,7 @@
|
|
|
101
101
|
|
|
102
102
|
<div id="toast" class="toast" role="status" aria-live="polite" data-visible="0"></div>
|
|
103
103
|
|
|
104
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
104
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
105
105
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
106
106
|
<script src="/builders/palette.js" defer></script>
|
|
107
107
|
<script src="/builders/dom-utils.js?v=2026-06-23-contrib"></script>
|
|
@@ -115,7 +115,7 @@
|
|
|
115
115
|
|
|
116
116
|
<div id="toast" class="toast" role="status" aria-live="polite" data-visible="0"></div>
|
|
117
117
|
|
|
118
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
118
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
119
119
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
120
120
|
<script src="/builders/palette.js" defer></script>
|
|
121
121
|
<!-- the shared markdown reader (window.OTBMdReader) — primer.js renders through
|
|
@@ -187,7 +187,7 @@
|
|
|
187
187
|
|
|
188
188
|
<!-- The app shell (sidebar + top bar). Dependency-free; loaded FIRST so the
|
|
189
189
|
chrome exists before the page script runs. -->
|
|
190
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
190
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
191
191
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
192
192
|
<script src="/builders/palette.js" defer></script>
|
|
193
193
|
<!-- shared frontend toolkit (window.OTB) — loaded before profile.js, which pulls from it. -->
|
|
@@ -58,7 +58,7 @@
|
|
|
58
58
|
|
|
59
59
|
<div id="toast" class="toast" role="status" aria-live="polite" data-visible="0"></div>
|
|
60
60
|
|
|
61
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
61
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
62
62
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
63
63
|
<script src="/builders/palette.js" defer></script>
|
|
64
64
|
<script src="/builders/dom-utils.js?v=2026-06-16-gate"></script>
|
|
@@ -68,7 +68,7 @@
|
|
|
68
68
|
|
|
69
69
|
<!-- The app shell (sidebar + top bar). Dependency-free; loaded FIRST so the
|
|
70
70
|
chrome exists before the page script runs. -->
|
|
71
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
71
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
72
72
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
73
73
|
<script src="/builders/palette.js" defer></script>
|
|
74
74
|
<!-- shared frontend toolkit (window.OTB) — loaded before ranks.js, which pulls from it. -->
|
|
@@ -41,7 +41,7 @@
|
|
|
41
41
|
|
|
42
42
|
<div id="toast" class="toast" role="status" aria-live="polite" data-visible="0"></div>
|
|
43
43
|
|
|
44
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
44
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
45
45
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
46
46
|
<script src="/builders/palette.js" defer></script>
|
|
47
47
|
<script src="/builders/dom-utils.js?v=2026-06-14-domutils"></script>
|
|
@@ -50,7 +50,7 @@
|
|
|
50
50
|
|
|
51
51
|
<!-- The app shell (sidebar + top bar). Dependency-free; loaded FIRST so the
|
|
52
52
|
chrome exists before the page script runs. -->
|
|
53
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
53
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
54
54
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
55
55
|
<script src="/builders/palette.js" defer></script>
|
|
56
56
|
<!-- shared frontend toolkit (window.OTB — rank labels, number formats) + the
|
|
@@ -99,7 +99,7 @@
|
|
|
99
99
|
|
|
100
100
|
<!-- The app shell (sidebar + top bar). Dependency-free; loaded FIRST so the
|
|
101
101
|
chrome exists before the page script runs. -->
|
|
102
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
102
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
103
103
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
104
104
|
<script src="/builders/palette.js" defer></script>
|
|
105
105
|
<!-- shared frontend toolkit (window.OTB) — loaded BEFORE sessions.js so it can pull from it. -->
|
|
@@ -400,7 +400,7 @@
|
|
|
400
400
|
|
|
401
401
|
<!-- The app shell (sidebar + top bar). Dependency-free; loaded FIRST so the
|
|
402
402
|
chrome exists before the page scripts run. -->
|
|
403
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
403
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
404
404
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
405
405
|
<script src="/builders/palette.js" defer></script>
|
|
406
406
|
<!-- shared frontend toolkit (window.OTB) — loaded before consuming IIFEs. -->
|
|
@@ -788,7 +788,7 @@
|
|
|
788
788
|
// not establish authority. null is NOT "holds nothing that matters": it is
|
|
789
789
|
// unreadable, and unreadable hides the link, the same call gateAllows()'s
|
|
790
790
|
// `default: false` and the social mode's OFF-is-the-fallback rule make.
|
|
791
|
-
var access = { authed: null, rank: null, graduated: false, showWork: false, permissions: null, needs: null };
|
|
791
|
+
var access = { authed: null, rank: null, graduated: false, showWork: false, permissions: null, needs: null, founding: null };
|
|
792
792
|
|
|
793
793
|
function gateAllows(gate) {
|
|
794
794
|
var authed = access.authed === true;
|
|
@@ -840,6 +840,79 @@
|
|
|
840
840
|
else delete root.dataset.social;
|
|
841
841
|
}
|
|
842
842
|
|
|
843
|
+
// PROJECT FOUNDING MODE (task 1004422 / BV2.PS03, goal 1000121). While a project is
|
|
844
|
+
// being founded, its EXISTING hall wears this mode — the owner's blend rule
|
|
845
|
+
// (docs/design/project-startup-direction.md): genesis never becomes a second hall.
|
|
846
|
+
// It adds exactly two things here and changes nothing else:
|
|
847
|
+
// - the founding band, a strip created ABOVE the topbar inside .app-body;
|
|
848
|
+
// - the asleep state on today's nav items, each saying which stage wakes it.
|
|
849
|
+
// The server decides which rooms sleep (/me.founding_mode.asleep, keyed by NAV id)
|
|
850
|
+
// and this never re-derives it — the social-mode precedent.
|
|
851
|
+
//
|
|
852
|
+
// OFF is the default and the fallback, and OFF REMOVES rather than hides: the band
|
|
853
|
+
// element and every asleep class and tag are taken out of the DOM, so a hall that
|
|
854
|
+
// is not founding is byte-for-byte the hall it was (tests/founding_mode.mjs pins
|
|
855
|
+
// it). Cosmetic only — an asleep room still opens; nothing is enforced (ADR 0016).
|
|
856
|
+
// The asleep tag in words a person would say, never a raw stage slug.
|
|
857
|
+
var WAKE_TEXT = {
|
|
858
|
+
scope: 'opens after scope', strategize: 'opens after strategy', charter: 'opens after the charter',
|
|
859
|
+
legalize: 'opens after legal setup', legislation: 'opens after legislation', alive: 'opens when alive'
|
|
860
|
+
};
|
|
861
|
+
function applyFounding() {
|
|
862
|
+
var f = access.founding;
|
|
863
|
+
var on = !!(f && f.active === true && f.asleep && typeof f.asleep === 'object');
|
|
864
|
+
var root = document.documentElement;
|
|
865
|
+
// The common case — a project that is not founding, on a page that never wore the
|
|
866
|
+
// mode — returns before touching a single node. That is the strongest form of the
|
|
867
|
+
// no-hijack condition: nothing is read, created, classed or removed.
|
|
868
|
+
if (!on && root.dataset.founding !== 'on') return;
|
|
869
|
+
document.querySelectorAll('#app-sidebar .nav-item--asleep').forEach(function (el) {
|
|
870
|
+
el.classList.remove('nav-item--asleep');
|
|
871
|
+
delete el.dataset.wakes;
|
|
872
|
+
var tag = el.querySelector('[data-wakes-tag]');
|
|
873
|
+
if (tag && tag.parentNode) tag.parentNode.removeChild(tag);
|
|
874
|
+
});
|
|
875
|
+
var band = document.getElementById('founding-band');
|
|
876
|
+
if (!on) {
|
|
877
|
+
delete root.dataset.founding;
|
|
878
|
+
if (band && band.parentNode) band.parentNode.removeChild(band);
|
|
879
|
+
return;
|
|
880
|
+
}
|
|
881
|
+
root.dataset.founding = 'on';
|
|
882
|
+
Object.keys(f.asleep).forEach(function (id) {
|
|
883
|
+
var el = document.getElementById('nav-' + id);
|
|
884
|
+
if (!el) return;
|
|
885
|
+
var stage = String(f.asleep[id]);
|
|
886
|
+
el.classList.add('nav-item--asleep');
|
|
887
|
+
el.dataset.wakes = stage;
|
|
888
|
+
var tag = document.createElement('span');
|
|
889
|
+
tag.className = 'nav-item__wakes';
|
|
890
|
+
tag.setAttribute('data-wakes-tag', '');
|
|
891
|
+
tag.textContent = WAKE_TEXT[stage] || 'opens later';
|
|
892
|
+
el.appendChild(tag);
|
|
893
|
+
});
|
|
894
|
+
if (!band) {
|
|
895
|
+
var body = document.querySelector('.app-body');
|
|
896
|
+
if (!body) return;
|
|
897
|
+
band = document.createElement('div');
|
|
898
|
+
band.id = 'founding-band';
|
|
899
|
+
band.className = 'founding-band';
|
|
900
|
+
band.setAttribute('role', 'status');
|
|
901
|
+
body.insertBefore(band, body.firstChild);
|
|
902
|
+
}
|
|
903
|
+
var name = (brand.identity && (brand.identity.productName || brand.identity.worldName)) || 'This project';
|
|
904
|
+
var stageText = f.stage === 'decide'
|
|
905
|
+
? 'deciding the plan'
|
|
906
|
+
: 'stage ' + f.stage_number + ' of ' + f.stage_count + ' \u00b7 ' + f.stage;
|
|
907
|
+
band.innerHTML =
|
|
908
|
+
'<span class="founding-band__dot" aria-hidden="true"></span>' +
|
|
909
|
+
'<span class="founding-band__title">Project founding mode</span>' +
|
|
910
|
+
'<span class="founding-band__desc">' + esc(name) + ' is still being founded. Rooms open as each stage finishes, and everyone who joins now becomes a founding builder.</span>' +
|
|
911
|
+
'<span class="founding-band__stage">' + esc(stageText) + (f.day ? ' \u00b7 day ' + esc(String(f.day)) : '') +
|
|
912
|
+
(Array.isArray(f.waiting_on) && f.waiting_on.length ? ' \u00b7 waiting on ' + esc(f.waiting_on.join(', ')) : '') + '</span>' +
|
|
913
|
+
'<a class="founding-band__link" href="/">What\u2019s this?</a>';
|
|
914
|
+
}
|
|
915
|
+
|
|
843
916
|
// task 1003117 (R06 of goal 1000074): EMPHASISE the Studio nav entry for a
|
|
844
917
|
// builder whose craft includes artist — the "emphasized entry for artist-craft
|
|
845
918
|
// builders" half of artist mode. Cosmetic only (the page is open to every rank,
|
|
@@ -917,6 +990,10 @@
|
|
|
917
990
|
access.needs = (state.needs && typeof state.needs === 'object') ? state.needs : null;
|
|
918
991
|
}
|
|
919
992
|
if ('social' in state) applySocial(state.social);
|
|
993
|
+
// task 1004422: stored as given — the object, or null (OFF).
|
|
994
|
+
if ('founding' in state) {
|
|
995
|
+
access.founding = (state.founding && typeof state.founding === 'object') ? state.founding : null;
|
|
996
|
+
}
|
|
920
997
|
if (state.builder) { renderUser(state.builder); applyCraftEmphasis(state.builder); }
|
|
921
998
|
}
|
|
922
999
|
document.querySelectorAll('#app-sidebar [data-gate]').forEach(function (el) {
|
|
@@ -930,6 +1007,8 @@
|
|
|
930
1007
|
// what settles. Reversing the order would badge an item still hidden from
|
|
931
1008
|
// the previous state.
|
|
932
1009
|
applyCounts();
|
|
1010
|
+
// task 1004422: after the gate loop, so the asleep tags land on the settled items.
|
|
1011
|
+
applyFounding();
|
|
933
1012
|
// AFTER the gate loop for the same reason applyCounts is: it reads the settled
|
|
934
1013
|
// permission map, which the loop above is what the shell has just been told.
|
|
935
1014
|
maybeRenderCoreUpdate();
|
|
@@ -1153,6 +1232,8 @@
|
|
|
1153
1232
|
// hall's Standing card and the CLI nudge read — no new route, no extra
|
|
1154
1233
|
// poll, and the badge cannot disagree with the roster it came from.
|
|
1155
1234
|
needs: me.needs || null,
|
|
1235
|
+
// task 1004422: project founding mode, for the band and the asleep rooms.
|
|
1236
|
+
founding: me.founding_mode || null,
|
|
1156
1237
|
builder: me.builder,
|
|
1157
1238
|
});
|
|
1158
1239
|
}).catch(function () { /* cosmetic only */ });
|
|
@@ -60,6 +60,14 @@
|
|
|
60
60
|
const GOLDEN = 137.50776405003785 * Math.PI / 180;
|
|
61
61
|
const reduce = !!(window.matchMedia && matchMedia('(prefers-reduced-motion: reduce)').matches);
|
|
62
62
|
const NOW = Date.now();
|
|
63
|
+
// task 1004402 (ADR 0351): a ring's UAT state, in the SAME words the goal page
|
|
64
|
+
// uses — read from criterion-uat-ui.js, which both sky pages load first. An
|
|
65
|
+
// open ring carries no label (its open ring already says so), and a missing
|
|
66
|
+
// script or an older server yields none rather than a guessed word.
|
|
67
|
+
function uatLabel(state) {
|
|
68
|
+
const labels = window.OTBCriterionUat && window.OTBCriterionUat.STATE_LABELS;
|
|
69
|
+
return labels && state && state !== 'open' ? labels[state] || null : null;
|
|
70
|
+
}
|
|
63
71
|
function hash(s) { let h = 2166136261; s = String(s); for (let i = 0; i < s.length; i++) { h ^= s.charCodeAt(i); h = Math.imul(h, 16777619); } return (h >>> 0) / 4294967296; }
|
|
64
72
|
function rng(seed) { let t = Math.floor(hash(seed) * 1e9) + 1; return () => { t += 0x6D2B79F5; let r = Math.imul(t ^ (t >>> 15), 1 | t); r ^= r + Math.imul(r ^ (r >>> 7), 61 | r); return ((r ^ (r >>> 14)) >>> 0) / 4294967296; }; }
|
|
65
73
|
const clamp = (v, a, b) => Math.max(a, Math.min(b, v));
|
|
@@ -138,7 +146,7 @@
|
|
|
138
146
|
return {
|
|
139
147
|
id: String(g.goal_id), title: g.title || 'A private goal', subtitle: g.subtitle || null, version: g.version_id, status: g.status,
|
|
140
148
|
taskTotal: Number(g.task_total) || 0, taskDone: Number(g.task_done) || 0, createdAt: g.created_at || null,
|
|
141
|
-
crit: (g.criteria || []).map((c) => ({ id: String(c.id), text: c.criterion_md || '', satisfied: c.satisfied === true, tasks: (c.task_ids || []).map(String), pendingReview: c.pending_review === true })),
|
|
149
|
+
crit: (g.criteria || []).map((c) => ({ id: String(c.id), text: c.criterion_md || '', satisfied: c.satisfied === true, tasks: (c.task_ids || []).map(String), pendingReview: c.pending_review === true, uat: c.uat_state || null, uatLabel: uatLabel(c.uat_state), backendOnly: c.backend_only === true })),
|
|
142
150
|
tasks: (g.tasks || []).map((t) => ({ id: String(t.id), title: t.title || 'a task', status: t.status, credits: t.credits_reward == null ? 0 : Number(t.credits_reward), createdAt: t.created_on || null, sourceRef: t.idea_id != null ? String(t.idea_id) : null })),
|
|
143
151
|
};
|
|
144
152
|
}
|
|
@@ -31,7 +31,7 @@
|
|
|
31
31
|
if (!h || h.kind === 'shuttle') { card.classList.remove('on'); card.setAttribute('aria-hidden', 'true'); return; }
|
|
32
32
|
const { goalById } = S; let html = '';
|
|
33
33
|
if (h.kind === 'idea') { const i = h.ref; const o = OBJ[i.st] || { noun: i.st, word: i.st }; const wellG = i.well && goalById.get(i.well); const r = reach(i).length; html = `<div class="k">${glyphHtml(i)}<span class="lbl${i.st === 'star' ? ' hot' : ''}">${o.noun} · ${o.word}${i.origin === 'claude' ? ' · filed by a session' : ''}</span></div><div class="t">${esc(i.title)}</div><div class="m">${i.shaped ? `<b>${i.shaped.kind === 'goal' ? 'became this goal' : 'became a ring'}</b> · ` : ''}${wellG ? `caught by <b>${esc(short(wellG.title))}</b>` : `open space · ${Math.round(i.age)} days adrift`} · ${esc(became(i))}${i.size && i.size.credits ? ` · size <b>${i.size.credits}</b>` : ''}${i.lit < 1 ? ` · <b>${Math.round(i.lit * 100)}%</b> alive` : ''}${r ? ' · its reach is drawn' : ''}</div>`; }
|
|
34
|
-
else if (h.kind === 'ring') { const c = h.ref; const g = h.goal; html = `<div class="k"><span class="mk well" style="${c.satisfied ? 'border-style:solid;border-color:rgba(255,255,255,.7)' : ''}"></span><span class="lbl">ring ${h.index + 1} of ${g.crit.length} · ${c.satisfied ? 'closed' : 'open'}</span></div><div class="t">${esc(SKY.plain(c.text).slice(0, 180))}${SKY.plain(c.text).length > 180 ? '…' : ''}</div><div class="m">${c.tasks.length ? `<b>${c.tasks.length}</b> task${c.tasks.length === 1 ? '' : 's'} on this ring · <b>${c.credits}</b> credits` : 'no task gates it yet'}${c.pendingReview ? ' · awaiting review' : ''}${c.bornOf ? ` · <b style="color:var(--accent)">born of a thought</b>: ${esc(ideaTitle(c.bornOf))}` : ''}</div>`; }
|
|
34
|
+
else if (h.kind === 'ring') { const c = h.ref; const g = h.goal; html = `<div class="k"><span class="mk well" style="${c.satisfied ? 'border-style:solid;border-color:rgba(255,255,255,.7)' : ''}"></span><span class="lbl">ring ${h.index + 1} of ${g.crit.length} · ${c.satisfied ? 'closed' : 'open'}</span></div><div class="t">${esc(SKY.plain(c.text).slice(0, 180))}${SKY.plain(c.text).length > 180 ? '…' : ''}</div><div class="m">${c.tasks.length ? `<b>${c.tasks.length}</b> task${c.tasks.length === 1 ? '' : 's'} on this ring · <b>${c.credits}</b> credits` : 'no task gates it yet'}${c.uatLabel ? ` · ${esc(c.uatLabel)}` : (c.pendingReview && !c.uat ? ' · awaiting review' : '')}${c.backendOnly ? ' · backend-only' : ''}${c.bornOf ? ` · <b style="color:var(--accent)">born of a thought</b>: ${esc(ideaTitle(c.bornOf))}` : ''}</div>`; }
|
|
35
35
|
else if (h.kind === 'goal') { const g = h.ref; if (!seen(g)) html = `<div class="k"><span class="mk unseen"></span><span class="lbl">unexplored</span></div><div class="t">Something is here.</div><div class="m">Follow a route from a goal you know to reach it — or turn explore off to see everything.</div>`; else { const met = g.crit.filter((c) => c.satisfied).length; const state = g.status === 'open' ? (g.live > 0 ? 'gravity well · alive' : 'gravity well') : g.status === 'achieved' ? 'settled system' : 'collapsed'; html = `<div class="k"><span class="mk ${g.status === 'open' ? (g.live > 0 ? 'alive' : 'well') : g.status === 'achieved' ? 'settled' : 'collapsed'}"></span><span class="lbl${g.live > 0 ? ' hot' : ''}">${state} · ${esc(g.band.label)}</span></div><div class="t">${esc(g.title)}</div><div class="m"><b>${g.taskDone}</b> of <b>${g.taskTotal}</b> tasks${g.credits ? ` · <b>${g.credits}</b> credits` : ''} · ${g.crit.length ? `<b>${met}</b> of <b>${g.crit.length}</b> rings closed` : 'no rings written'}${g.live > 0 ? ` · <b>${g.active}</b> held now, <b>${g.recent}</b> landed this week` : ''}${g.thoughts.filter(inLayer).length ? ` · <b>${g.thoughts.filter(inLayer).length}</b> of your thoughts` : ''}${g.bornOf ? ` · <b style="color:var(--accent)">born of a thought</b>` : ''}${edgesOf(g).length ? ` · <b>${edgesOf(g).length}</b> route${edgesOf(g).length === 1 ? '' : 's'}` : ''}</div>`; } }
|
|
36
36
|
else if (h.kind === 'task' || h.kind === 'ltask') { const t = h.ref; const kin = t.goal && t.kin ? t.goal.tasks.filter((x) => x.kin === t.kin && x !== t).length : 0; html = `<div class="k"><span class="mk task${t.status === 'active' ? ' live' : ''}"></span><span class="lbl${t.status === 'active' ? ' hot' : ''}">task · ${esc(t.status)}</span></div><div class="t">${esc(t.title)}</div><div class="m">${t.credits != null ? `<b>${t.credits}</b> credits · ` : ''}${t.ci >= 0 ? `ring ${t.ci + 1}` : 'outer orbit'}${t.sourceRef ? ' · born of a thought' : ''}${kin ? ` · lines up with <b>${kin}</b> kin` : ''}${t.drift ? ' · in motion' : ''}</div>`; }
|
|
37
37
|
else if (h.kind === 'stub') { const e = h.edge; const waits = e.a === h.goal; html = `<div class="k"><span class="mk route"></span><span class="lbl chart">route · ${waits ? 'waits on' : 'waited on by'}</span></div><div class="t">${seen(h.other) ? esc(h.other.title) : 'an unexplored goal'}</div><div class="m"><b>${e.count}</b> task dependenc${e.count === 1 ? 'y' : 'ies'} · click to chart it · double-click to chart every route from here</div>`; }
|
|
@@ -78,7 +78,7 @@
|
|
|
78
78
|
${waiting.length ? fact('waits on', waiting.map(name).join(', ')) : ''}
|
|
79
79
|
${waitedOn.length ? fact('waited on by', waitedOn.map(name).join(', ')) : ''}
|
|
80
80
|
</div>
|
|
81
|
-
${g.crit.length ? `<ul class="crit">${g.crit.slice(0, 10).map((c) => `<li><span class="ring${c.satisfied ? ' on' : ''}"></span><span>${esc(plain(c.text).slice(0, 120))}${plain(c.text).length > 120 ? '…' : ''}${c.bornOf ? ` <span class="born">· born of a thought</span>` : ''}${c.credits ? ` <span class="lbl">${c.credits} cr</span>` : ''}</span></li>`).join('')}</ul>` : ''}
|
|
81
|
+
${g.crit.length ? `<ul class="crit">${g.crit.slice(0, 10).map((c) => `<li><span class="ring${c.satisfied ? ' on' : ''}"></span><span>${esc(plain(c.text).slice(0, 120))}${plain(c.text).length > 120 ? '…' : ''}${c.bornOf ? ` <span class="born">· born of a thought</span>` : ''}${c.credits ? ` <span class="lbl">${c.credits} cr</span>` : ''}${c.uatLabel ? ` <span class="lbl">${esc(c.uatLabel)}</span>` : ''}${c.backendOnly ? ' <span class="lbl">backend-only</span>' : ''}</span></li>`).join('')}</ul>` : ''}
|
|
82
82
|
<div class="doors">
|
|
83
83
|
<button type="button" class="door primary" id="descendBtn">${g.status === 'open' ? 'descend into the well' : 'look closer'}</button>
|
|
84
84
|
${edgesOf(g).length ? `<button type="button" class="door" id="chartBtn">chart its routes</button>` : ''}
|
|
@@ -176,7 +176,7 @@
|
|
|
176
176
|
|
|
177
177
|
<div id="toast" class="toast" role="status" aria-live="polite" data-visible="0"></div>
|
|
178
178
|
|
|
179
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
179
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
180
180
|
<script src="/builders/palette.js" defer></script>
|
|
181
181
|
<script src="/builders/dom-utils.js?v=2026-06-23-contrib"></script>
|
|
182
182
|
<!-- The kit, for its ONE renderer: the full-size ship-time visual figure
|
|
@@ -667,6 +667,42 @@ main:focus { outline: none; }
|
|
|
667
667
|
.nav-item--craft .nav-icon,
|
|
668
668
|
.nav-item--craft .nav-item__label { color: var(--accent-ink); }
|
|
669
669
|
|
|
670
|
+
/* task 1004422 (BV2.PS03): PROJECT FOUNDING MODE. The hall wears it; it never
|
|
671
|
+
becomes a second hall (the blend rule, docs/design/project-startup-direction.md).
|
|
672
|
+
Two additions only, both created by shell.js while /me says founding and REMOVED
|
|
673
|
+
when it does not: the band above the topbar, and today's nav items dimmed with
|
|
674
|
+
the stage that wakes them. The band is live state, so its dot takes the accent;
|
|
675
|
+
the wake tag reads only in the open rail, like the labels. */
|
|
676
|
+
.founding-band {
|
|
677
|
+
display: flex;
|
|
678
|
+
align-items: center;
|
|
679
|
+
gap: 12px;
|
|
680
|
+
min-height: 44px;
|
|
681
|
+
padding: 0 22px;
|
|
682
|
+
background: color-mix(in srgb, var(--accent) 14%, var(--bg));
|
|
683
|
+
border-bottom: 1px solid color-mix(in srgb, var(--accent) 36%, transparent);
|
|
684
|
+
font-size: 13px;
|
|
685
|
+
color: var(--ink-soft);
|
|
686
|
+
}
|
|
687
|
+
.founding-band__dot { width: 8px; height: 8px; border-radius: 50%; background: var(--accent); flex: none; }
|
|
688
|
+
.founding-band__title { font-size: 11.5px; font-weight: 600; letter-spacing: 0.12em; text-transform: uppercase; color: var(--ink); white-space: nowrap; }
|
|
689
|
+
.founding-band__desc { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
|
|
690
|
+
.founding-band__stage { margin-left: auto; font-size: 12px; color: var(--accent-ink); white-space: nowrap; }
|
|
691
|
+
/* The prose-link 24px floor convention: width bought with padding, handed back with
|
|
692
|
+
an equal negative margin, so the target grows and the row does not re-space. */
|
|
693
|
+
.founding-band__link { padding: 10px 6px; margin: 0 -6px; color: var(--ink); text-decoration: underline; text-underline-offset: 3px; white-space: nowrap; }
|
|
694
|
+
/* Phone: the row wraps instead of widening the page (the no-sideways rule the kit
|
|
695
|
+
measured), and the long sentence steps aside for the stage and the link. */
|
|
696
|
+
@media (max-width: 640px) {
|
|
697
|
+
.founding-band { flex-wrap: wrap; row-gap: 2px; padding: 8px 16px; }
|
|
698
|
+
.founding-band__desc { display: none; }
|
|
699
|
+
.founding-band__stage { margin-left: 0; white-space: normal; }
|
|
700
|
+
}
|
|
701
|
+
.nav-item--asleep { opacity: 0.55; }
|
|
702
|
+
.nav-item__wakes { display: none; margin-left: auto; font-size: 10px; letter-spacing: 0.08em; text-transform: uppercase; color: var(--ink-faint); }
|
|
703
|
+
.app-sidebar:hover .nav-item__wakes,
|
|
704
|
+
.app-sidebar:focus-within .nav-item__wakes { display: inline; }
|
|
705
|
+
|
|
670
706
|
/* task 1003737: the nav count badge — the hall's only badge mechanism, built
|
|
671
707
|
once and generically (shell.js `count:` names a need id; see the NAV model).
|
|
672
708
|
ABSOLUTE, not inline, because the rail has two shapes: it is a 64px icon strip
|
|
@@ -57,7 +57,7 @@
|
|
|
57
57
|
|
|
58
58
|
<!-- The app shell (sidebar + top bar + footer). Dependency-free; runs at parse
|
|
59
59
|
time so the chrome exists before the deferred page scripts execute. -->
|
|
60
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
60
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
61
61
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
62
62
|
<script src="/builders/palette.js" defer></script>
|
|
63
63
|
<!-- shared frontend toolkit (window.OTB) — loaded FIRST so task.js can pull from it. -->
|
|
@@ -138,15 +138,17 @@
|
|
|
138
138
|
</div>
|
|
139
139
|
</div>
|
|
140
140
|
|
|
141
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
141
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
142
142
|
<script src="/builders/palette.js" defer></script>
|
|
143
143
|
|
|
144
144
|
<script src="/builders/idea-objects.js?v=2026-09-27-split"></script>
|
|
145
|
-
|
|
145
|
+
<!-- task 1004402: the UAT state words the rings share with the goal page. -->
|
|
146
|
+
<script src="/builders/criterion-uat-ui.js?v=2026-09-30-uat1"></script>
|
|
147
|
+
<script src="/builders/sky-data.js?v=2026-09-30-uat1"></script>
|
|
146
148
|
<script src="/builders/sky-layout.js?v=2026-09-27-split"></script>
|
|
147
149
|
<script src="/builders/sky-draw.js?v=2026-09-27-split"></script>
|
|
148
|
-
<script src="/builders/sky-interaction.js?v=2026-09-
|
|
149
|
-
<script src="/builders/sky-panel.js?v=2026-09-
|
|
150
|
+
<script src="/builders/sky-interaction.js?v=2026-09-30-uat1"></script>
|
|
151
|
+
<script src="/builders/sky-panel.js?v=2026-09-30-uat1"></script>
|
|
150
152
|
<script src="/builders/sky-composer.js?v=2026-09-27-split"></script>
|
|
151
153
|
<script src="/builders/sky-tour.js?v=2026-09-27-split"></script>
|
|
152
154
|
</body>
|
|
@@ -140,7 +140,7 @@
|
|
|
140
140
|
|
|
141
141
|
<div id="toast" class="toast" role="status" aria-live="polite" data-visible="0"></div>
|
|
142
142
|
|
|
143
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
143
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
144
144
|
<script src="/builders/palette.js" defer></script>
|
|
145
145
|
<script src="/builders/dom-utils.js?v=2026-06-23-contrib"></script>
|
|
146
146
|
<script src="/builders/brand-holes.js?v=2026-09-29-aqfix"></script>
|
|
@@ -162,7 +162,7 @@
|
|
|
162
162
|
|
|
163
163
|
<!-- The app shell (sidebar + top bar). Dependency-free; loaded FIRST so the
|
|
164
164
|
chrome exists before the page script runs. -->
|
|
165
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
165
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
166
166
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
167
167
|
<script src="/builders/palette.js" defer></script>
|
|
168
168
|
<!-- shared frontend toolkit (window.OTB) — loaded before watch.js, which pulls from it. -->
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
{
|
|
2
|
+
"_": "Project founding mode (task 1004422) on an ordinary hall page: the founding band above the topbar and today's nav items asleep, rendered from a /me that says founding (kit fixture me-founding.json, the real server shaper's output at stage strategize). The page itself is work.states.json's; only the identity differs. The no-founding case is every other hall states file.",
|
|
3
|
+
"page": "/builders/work",
|
|
4
|
+
"surface": "hall-ui",
|
|
5
|
+
"stub": {
|
|
6
|
+
"prefix": "/builders/",
|
|
7
|
+
"fixtures": {
|
|
8
|
+
"me": "me-founding"
|
|
9
|
+
}
|
|
10
|
+
},
|
|
11
|
+
"modeQuery": false,
|
|
12
|
+
"ignoreRequests": [
|
|
13
|
+
"/api/(gds|bongos)/me$",
|
|
14
|
+
"/api/(gds|bongos)/me/",
|
|
15
|
+
"/api/(gds|bongos)/tasks",
|
|
16
|
+
"/api/(gds|bongos)/claims",
|
|
17
|
+
"/api/(gds|bongos)/goals",
|
|
18
|
+
"/api/(gds|bongos)/inbox/",
|
|
19
|
+
"/api/(gds|bongos)/versions"
|
|
20
|
+
],
|
|
21
|
+
"ignoreConsole": [
|
|
22
|
+
"/api/(gds|bongos)/",
|
|
23
|
+
"\\b401\\b",
|
|
24
|
+
"\\b404\\b",
|
|
25
|
+
"Unauthorized",
|
|
26
|
+
"Not Found",
|
|
27
|
+
"load failed"
|
|
28
|
+
],
|
|
29
|
+
"states": {
|
|
30
|
+
"founding": {
|
|
31
|
+
"auth": true,
|
|
32
|
+
"expect": {
|
|
33
|
+
"visible": [
|
|
34
|
+
"#founding-band"
|
|
35
|
+
]
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
}
|
|
@@ -171,7 +171,7 @@
|
|
|
171
171
|
|
|
172
172
|
<!-- The app shell (sidebar + top bar + footer). Dependency-free; runs at parse
|
|
173
173
|
time so the chrome exists before the deferred page scripts execute. -->
|
|
174
|
-
<script src="/builders/shell.js?v=2026-09-30-commands"></script>
|
|
174
|
+
<script src="/builders/shell.js?v=2026-09-30-founding-commands"></script>
|
|
175
175
|
<!-- jump palette (Ctrl/Cmd-K). Optional by design: without it the shell's slot stays hidden. -->
|
|
176
176
|
<script src="/builders/palette.js" defer></script>
|
|
177
177
|
<!-- shared frontend toolkit (window.OTB) — loaded FIRST so work.js can pull from it. -->
|