Add a README glossary and intended scale; correct the TOKENS comment #184
@@ -6,6 +6,11 @@ at boot. Entries start at 0.3.0.
|
|||||||
|
|
||||||
## Unreleased
|
## Unreleased
|
||||||
|
|
||||||
|
### The README defines its terms and states its intended scale
|
||||||
|
|
||||||
|
A new Glossary defines host, manifest, chrome, nav fragment, permission token, system plugin and
|
||||||
|
denylist. It also states the scale Plainpages is sized for: a handful of plugins per deployment.
|
||||||
|
|
||||||
### The mobile nav stays reachable on engines without `:has()`
|
### The mobile nav stays reachable on engines without `:has()`
|
||||||
|
|
||||||
At 860px and narrower, an engine without `:has()` (Chromium below 105, such as webOS TV 22 and 23,
|
At 860px and narrower, an engine without `:has()` (Chromium below 105, such as webOS TV 22 and 23,
|
||||||
|
|||||||
@@ -73,6 +73,7 @@ From here, render real pages against the app shell and fetch upstream data — s
|
|||||||
- [Goals](#goals)
|
- [Goals](#goals)
|
||||||
- [Audience](#audience)
|
- [Audience](#audience)
|
||||||
- [Overview](#overview)
|
- [Overview](#overview)
|
||||||
|
- [Glossary](#glossary)
|
||||||
- [Users, groups & permissions](#users-groups--permissions)
|
- [Users, groups & permissions](#users-groups--permissions)
|
||||||
- [naming a permission](#naming-a-permission)
|
- [naming a permission](#naming-a-permission)
|
||||||
- [a worked example](#a-worked-example)
|
- [a worked example](#a-worked-example)
|
||||||
@@ -210,6 +211,29 @@ feature removes the need for JS (theme switching, popovers, disclosure) we use i
|
|||||||
avoid is shipping a client-side runtime, not using the platform. Markup is semantic and accessible
|
avoid is shipping a client-side runtime, not using the platform. Markup is semantic and accessible
|
||||||
(see [AGENTS.md](AGENTS.md)).
|
(see [AGENTS.md](AGENTS.md)).
|
||||||
|
|
||||||
|
## Glossary
|
||||||
|
|
||||||
|
- **Host** — the `web` container: the Node process that discovers plugins, serves every page and
|
||||||
|
owns no state of its own. Everything outside it (a plugin's upstream, Ory) is reached over the network.
|
||||||
|
- **Plugin** — a folder under `plugins/` that adds domain screens; the only way to add a feature.
|
||||||
|
- **Manifest** — the object a plugin's `index.ts` exports through `definePlugin`: its routes, nav,
|
||||||
|
permissions and hooks. The host checks it at boot and refuses a bad one ([The manifest](#the-manifest)).
|
||||||
|
- **Chrome** — everything on a page that isn't the page's own content: brand, menu, user, theme and
|
||||||
|
CSRF token. A handler gets it as `ctx.chrome` ([RequestContext](#requestcontext)).
|
||||||
|
- **Nav fragment** — the `nav` entries one plugin contributes. The host merges every plugin's
|
||||||
|
fragment into the one global menu and filters it per user ([The menu system](#the-menu-system)).
|
||||||
|
- **Permission token** — a `<resource>:<action>` string such as `shifts:write`, granted in Keto and
|
||||||
|
carried in the session JWT's `permissions` claim ([Naming a permission](#naming-a-permission)).
|
||||||
|
- **System plugin** — a plugin that administers Plainpages' own identity stack, through the
|
||||||
|
privileged `ctx.system` ([System capabilities](#system-capabilities-the-ctxsystem-surface)).
|
||||||
|
- **Denylist** — the optional in-memory list of subjects revoked just now, so a permission change
|
||||||
|
lands before the JWT expires ([Instant revoke](#instant-revoke-the-optional-denylist)).
|
||||||
|
|
||||||
|
**Intended scale.** One deployment serves a handful of plugins, up to about ten, so a plugin's own
|
||||||
|
dependency tree ([Plugin dependencies](#plugin-dependencies)) costs disk and memory in proportion to
|
||||||
|
how many are installed. The `web` container scales out because it is stateless ([Stateless
|
||||||
|
core](#stateless-core)); a catalogue of hundreds of plugins is not a goal.
|
||||||
|
|
||||||
## Users, groups & permissions
|
## Users, groups & permissions
|
||||||
|
|
||||||
Authorization here is two hops: a **user** — directly, or through a **group** — is granted a
|
Authorization here is two hops: a **user** — directly, or through a **group** — is granted a
|
||||||
|
|||||||
@@ -9,14 +9,17 @@
|
|||||||
/* ---------- 1. TOKENS ----------------------------------------
|
/* ---------- 1. TOKENS ----------------------------------------
|
||||||
Two raw palettes (--l-* light, --d-* dark) are defined once.
|
Two raw palettes (--l-* light, --d-* dark) are defined once.
|
||||||
A small mapping (--bg: var(--l-bg) ...) picks the active set.
|
A small mapping (--bg: var(--l-bg) ...) picks the active set.
|
||||||
Theme resolution (no JS):
|
Theme resolution (no JS), every rule below needing :has():
|
||||||
• default + @media(dark) → follows the OS (Auto)
|
• default + @media(dark) → follows the OS (Auto)
|
||||||
• html:has(#theme-light) → force light
|
• html:has(#theme-light) → force light
|
||||||
• html:has(#theme-dark) → force dark
|
• html:has(#theme-dark) → force dark
|
||||||
|
Engines without :has() (Chromium below 105, Firefox below 121)
|
||||||
|
ignore all three and stay light; see the @supports not
|
||||||
|
selector(:has(a)) block further down.
|
||||||
We avoid light-dark()/color-scheme for app colors because their
|
We avoid light-dark()/color-scheme for app colors because their
|
||||||
resolution is unreliable across engines; :has() variable swaps
|
resolution is unreliable across engines. color-scheme is still
|
||||||
are rock-solid. color-scheme is still set as a hint for native
|
set as a hint for native widgets (date picker, scrollbars,
|
||||||
widgets (date picker, scrollbars, selects).
|
selects).
|
||||||
------------------------------------------------------------- */
|
------------------------------------------------------------- */
|
||||||
:root {
|
:root {
|
||||||
/* Hex, never oklch: below Chromium 111 `var(--accent)` is invalid at computed-value time and the
|
/* Hex, never oklch: below Chromium 111 `var(--accent)` is invalid at computed-value time and the
|
||||||
|
|||||||
@@ -12,13 +12,11 @@
|
|||||||
|
|
||||||
| ID | Release | Blocked by | Exempt | Item | L | E | I | R | S | Moves | Score |
|
| ID | Release | Blocked by | Exempt | Item | L | E | I | R | S | Moves | Score |
|
||||||
|---|---|---|---|---|---|---|---|---|---|---|---|
|
|---|---|---|---|---|---|---|---|---|---|---|---|
|
||||||
| 26 | 0.4.21 | | | **Add a domain glossary and the project's intended horizon to the README.** | 1 | 2 | 1 | 2 | 3 | 9 by 3, code health by 2 | 11.9 |
|
|
||||||
| 8 | 0.4.21 | | | **Run the visual E2E specs at viewports from a large desktop down to a small phone.** | 2 | 1 | 1 | 2 | 4 | code health by 3 | 9.0 |
|
| 8 | 0.4.21 | | | **Run the visual E2E specs at viewports from a large desktop down to a small phone.** | 2 | 1 | 1 | 2 | 4 | code health by 3 | 9.0 |
|
||||||
| 9 | 0.4.21 | | | **Typecheck `e2e-tests/` in the gate.** | 1 | 1 | 1 | 1 | 3 | code health by 2 | 9.0 |
|
| 9 | 0.4.21 | | | **Typecheck `e2e-tests/` in the gate.** | 1 | 1 | 1 | 1 | 3 | code health by 2 | 9.0 |
|
||||||
| 24 | 0.4.21 | | | **Retire `src/ui/shell-context.ts` and render the dashboard from `ctx.chrome`.** | 2 | 1 | 2 | 3 | 4 | code health by 3 | 9.0 |
|
| 24 | 0.4.21 | | | **Retire `src/ui/shell-context.ts` and render the dashboard from `ctx.chrome`.** | 2 | 1 | 2 | 3 | 4 | code health by 3 | 9.0 |
|
||||||
| 17 | 0.4.21 | | | **Remove the icons no caller uses from `ICON_NAMES` and the sprite.** | 1 | 1 | 1 | 1 | 1 | 8 by 1, code health by 1 | 8.8 |
|
| 17 | 0.4.21 | | | **Remove the icons no caller uses from `ICON_NAMES` and the sprite.** | 1 | 1 | 1 | 1 | 1 | 8 by 1, code health by 1 | 8.8 |
|
||||||
| 21 | 0.4.21 | | | **Fail the gate on a function that exceeds a size or complexity limit.** | 3 | 1 | 1 | 3 | 5 | code health by 4 | 7.2 |
|
| 21 | 0.4.21 | | | **Fail the gate on a function that exceeds a size or complexity limit.** | 3 | 1 | 1 | 3 | 5 | code health by 4 | 7.2 |
|
||||||
| 38 | 0.4.21 | | | **Correct the TOKENS comment at the top of `public/css/styles.css` so it no longer claims `:has()` swaps are "rock-solid" or that the theme follows the OS on every engine.** | 1 | 2 | 1 | 2 | 1 | code health by 1 | 7.2 |
|
|
||||||
| 32 | 0.4.21 | | | **Fail the gate on a stylesheet feature the browser floor lacks, unless it is guarded.** | 3 | 1 | 1 | 3 | 4 | code health by 2 | 6.0 |
|
| 32 | 0.4.21 | | | **Fail the gate on a stylesheet feature the browser floor lacks, unless it is guarded.** | 3 | 1 | 1 | 3 | 4 | code health by 2 | 6.0 |
|
||||||
| 20 | 0.4.21 | | | **Redirect an anonymous hit on a session-needing flow page to sign-in, instead of a 500.** | 2 | 2 | 2 | 4 | 3 | 2 by 4 | 4.2 |
|
| 20 | 0.4.21 | | | **Redirect an anonymous hit on a session-needing flow page to sign-in, instead of a 500.** | 2 | 2 | 2 | 4 | 3 | 2 by 4 | 4.2 |
|
||||||
| 4 | 0.4.21 | | | **Refuse a permission save whose baseline no longer matches Keto, so concurrent edits are not silently lost.** | 2 | 2 | 2 | 4 | 4 | 2 by 4 | 2.8 |
|
| 4 | 0.4.21 | | | **Refuse a permission save whose baseline no longer matches Keto, so concurrent edits are not silently lost.** | 2 | 2 | 2 | 4 | 4 | 2 by 4 | 2.8 |
|
||||||
@@ -39,12 +37,6 @@
|
|||||||
|
|
||||||
## Details
|
## Details
|
||||||
|
|
||||||
### 26. Add a domain glossary and the project's intended horizon to the README.
|
|
||||||
|
|
||||||
Glossary: host, manifest, chrome, nav fragment, permission token, system plugin, denylist. Also the
|
|
||||||
expected plugin count, since per-plugin dependency isolation prices N dependency trees on disk and
|
|
||||||
in RSS.
|
|
||||||
|
|
||||||
### 24. Retire `src/ui/shell-context.ts` and render the dashboard from `ctx.chrome`.
|
### 24. Retire `src/ui/shell-context.ts` and render the dashboard from `ctx.chrome`.
|
||||||
|
|
||||||
`ShellModel`/`buildShellContext` has one consumer, the dashboard, and duplicates `PageChrome` on
|
`ShellModel`/`buildShellContext` has one consumer, the dashboard, and duplicates `PageChrome` on
|
||||||
@@ -59,14 +51,6 @@ AGENTS.md → "`ICON_NAMES` is a host-owned registry" already makes this routine
|
|||||||
|
|
||||||
Only `tsc --strict` runs today. A new tool is a new dependency, so justify it.
|
Only `tsc --strict` runs today. A new tool is a new dependency, so justify it.
|
||||||
|
|
||||||
### 38. Correct the TOKENS comment at the top of `public/css/styles.css` so it no longer claims `:has()` swaps are "rock-solid" or that the theme follows the OS on every engine.
|
|
||||||
|
|
||||||
Section 1's TOKENS comment says the theme follows the OS by default and that `:has()` variable swaps
|
|
||||||
are "rock-solid". On an engine without `:has()` (Chromium below 105, Firefox below 121) every theme
|
|
||||||
rule is inert, the OS-dark rule included, so those engines stay light, as the
|
|
||||||
`@supports not selector(:has(a))` block further down says. A reader trusting the comment expects dark
|
|
||||||
mode there.
|
|
||||||
|
|
||||||
### 32. Fail the gate on a stylesheet feature the browser floor lacks, unless it is guarded.
|
### 32. Fail the gate on a stylesheet feature the browser floor lacks, unless it is guarded.
|
||||||
|
|
||||||
Nothing checks README → "Two browser floors", and no E2E engine is old enough to show a break.
|
Nothing checks README → "Two browser floors", and no E2E engine is old enough to show a break.
|
||||||
|
|||||||
Reference in New Issue
Block a user