@the-portland-company/shell 0.45.0 → 0.47.0-rc.1

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/CHANGELOG.md CHANGED
@@ -1,3 +1,120 @@
1
+ ## 0.47.0 — 2026-08-13
2
+
3
+ Petition Mode has been green since V1 and has rendered red for the whole of the
4
+ 0.4x chrome. This release fixes the cause rather than the symptom, and the cause
5
+ turned out to be a platform bug that affects everyone.
6
+
7
+ **Opt-in with byte-identical defaults.** Every change below is additive. An app
8
+ that declares nothing renders exactly as it did on 0.46.0 — the tests assert the
9
+ fallbacks explicitly, not just the new behaviour.
10
+
11
+ ### Fixed — the chrome painted its UI furniture with a political party colour
12
+
13
+ `--color-race-red` is the PARTY identity token, the one the party-share charts
14
+ use for Republican. The chrome used it directly in 32 places as its UI accent:
15
+ the mode pill, the org badge, active nav rows, the avatar circle, focus rings,
16
+ primary buttons, the nav hover sweep.
17
+
18
+ Besides mis-signalling, it made the accent unoverridable — apps reasonably set
19
+ `--color-accent` and nothing happened, because nothing read it.
20
+
21
+ Those 32 references now resolve a semantic token, split by what the colour
22
+ actually means: `--color-accent` for genuine accent furniture, and a new
23
+ `--color-danger` for attention and error (count badges, the low-fuel meter and
24
+ its nudge, validation messages). The danger set stays red in every Mode — a
25
+ green "3 unread" badge is worse than a red one.
26
+
27
+ `chrome.css` defines both as `var(--color-race-red)`, so **no pixels move**.
28
+ The last hardcoded accent literal went too: the nav hover sweep's
29
+ `linear-gradient(90deg,#EA4751 0%,#E63946 100%)` is now `--nav-hover-gradient`,
30
+ defaulted to those same two ramp stops.
31
+
32
+ Red ramp STOPS (`--color-race-red-400` etc.) are unchanged — the red ramp is
33
+ legitimately the red ramp. It was the semantic "this is our accent" use that was
34
+ wrong.
35
+
36
+ ### Added — one accent per Mode
37
+
38
+ A Mode may now carry its own chrome accent; the platform keeps one accent by
39
+ default.
40
+
41
+ `NavAppShell` stamps `data-politogy-mode` on its root, sourced by
42
+ `PolitogyAppFrame` from the `POLITOGY_APPS` registry — never from a prop an app
43
+ passes, so an app still cannot pick its own chrome colour; it inherits its
44
+ Mode's. The Brand API serves a Mode's values as
45
+ `[data-politogy-mode="petition"] { --mode-accent: … }` and `chrome.css`
46
+ re-declares the aliases on that element:
47
+
48
+ ```css
49
+ [data-politogy-mode] {
50
+ --color-accent: var(--mode-accent, var(--color-race-red));
51
+ }
52
+ ```
53
+
54
+ The placement is load-bearing: a custom property is substituted at
55
+ computed-value time on the element it is declared on, so declaring this at
56
+ `:root` would resolve `--mode-accent` there (unset) and inherit the fallback
57
+ down — the Mode block could never win.
58
+
59
+ A Mode that declares no chrome group leaves `--mode-accent` unset and every
60
+ line falls back to its pre-0.47 value. Relationship and Campaign declare none;
61
+ unscoped apps carry no attribute at all, so the block does not even match them.
62
+
63
+ Dark mode keeps the platform's neutral ramp. The Brand sheet resets the Mode
64
+ SURFACES to the guaranteed-invalid value under `.dark` so they fall through to
65
+ the neutrals; only the accent, a foreground colour, carries over.
66
+
67
+ Active sub-rows also gain a 3px left rail drawn from `--nav-row-active-rail`,
68
+ which resolves `transparent` unless the Mode declared a chrome group — so for
69
+ every other app the span renders invisible and out of flow.
70
+
71
+ Needs the matching Brand API release (`tokens.modes.<id>.chrome`).
72
+
73
+ ### Added — `NavItem { kind: 'section' }`, non-interactive section rows
74
+
75
+ V1's rail grouped eleven rows under MANAGE / PIPELINE / PEOPLE / SYSTEM. 0.43
76
+ dropped the capability; this restores it.
77
+
78
+ `kind` is optional and defaults to `'link'`, so every existing `NavItem[]` keeps
79
+ its type and rendering. It is a widened field rather than a discriminated union
80
+ on purpose — a union would make `item.href` a type error for every consumer that
81
+ reads it, turning an additive feature into a breaking change.
82
+
83
+ It is also not the `disabled`-row trick apps have been faking it with: that
84
+ renders `aria-disabled`, which announces a heading as an unavailable CONTROL. A
85
+ section carries no control semantics at all.
86
+
87
+ Rendered at both nesting levels, so an app that nests its tree under a standard
88
+ nav entry (Petitions) gets its sections inside the expanded group too.
89
+
90
+ ### Added — registry-granted frame inputs
91
+
92
+ `contentWrapper` and `page.breadcrumbs` existed but were gated to the core app,
93
+ which left Petitions with a 1280px centred box around a 1550px left-aligned page
94
+ container, and a trail reading "Dashboard › Adjudication" on every adjudication
95
+ URL including a specific sheet and line.
96
+
97
+ Rather than widening the `app === CORE_APP` gate — which would let any app
98
+ re-specify any chrome element — the exception is declared in the registry:
99
+
100
+ ```ts
101
+ petitions: { …, grants: ['contentWrapper', 'breadcrumbs'] }
102
+ ```
103
+
104
+ `data.frame.<field>` is honoured only when the app's registry row lists it. An
105
+ app cannot grant itself, the complete set of exceptions is one greppable table,
106
+ and an ungranted app that passes the prop gets `undefined` — "no effect", never
107
+ a silent effect.
108
+
109
+ A grant is for a fact only the app HAS, never for a look.
110
+
111
+ ### Changed — prereleases publish under the `next` dist-tag
112
+
113
+ `npm publish` tags `latest` whatever the semver, so an rc would silently become
114
+ what a fresh `npm i @the-portland-company/shell` resolves to across the estate.
115
+ The release workflow now detects a prerelease version and publishes it under
116
+ `next`, leaving `latest` on the last stable release until the promotion tag.
117
+
1
118
  ## 0.41.1 — 2026-08-03
2
119
 
3
120
  ### Fixed — the Chakra tooltip override in 0.41.0 did not actually take