@echelon-foundry/design-system 0.2.0 → 0.3.0-main.216.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/LICENSE +21 -0
- package/README.md +46 -0
- package/dist/all.css +5537 -841
- package/dist/assessment.css +55 -12
- package/dist/build-metrics.json +181 -5
- package/dist/components.css +2965 -36
- package/dist/foundations.css +90 -0
- package/dist/marketing/forma-all.css +8162 -0
- package/dist/marketing/forma-echelon-marketing.css +2109 -0
- package/dist/marketing/forma-marketing-theme-echelon.css +163 -0
- package/dist/marketing/forma-marketing.css +1947 -0
- package/dist/marketing/forma-marketing.manifest.json +52 -0
- package/dist/marketing/forma-marketing.sha256 +4 -0
- package/dist/marketing.css +1198 -0
- package/dist/patterns/active-filter-summary.html +10 -0
- package/dist/patterns/attention-path.html +29 -0
- package/dist/patterns/badge.html +9 -0
- package/dist/patterns/callout.html +23 -0
- package/dist/patterns/card-grid.html +25 -0
- package/dist/patterns/character-grid-3270.html +39 -0
- package/dist/patterns/character-grid-field.html +21 -0
- package/dist/patterns/character-grid-keys.html +20 -0
- package/dist/patterns/character-grid-reveal.html +16 -0
- package/dist/patterns/character-grid-selection.html +30 -0
- package/dist/patterns/character-grid-status.html +11 -0
- package/dist/patterns/character-grid-workflow.html +147 -0
- package/dist/patterns/character-grid.html +16 -0
- package/dist/patterns/cluster.html +5 -0
- package/dist/patterns/code-sample.html +9 -0
- package/dist/patterns/command-group.html +6 -0
- package/dist/patterns/comparison-grid.html +7 -0
- package/dist/patterns/comparison-pairs.html +13 -0
- package/dist/patterns/cta.html +12 -0
- package/dist/patterns/dense-ledger.html +7 -0
- package/dist/patterns/diagnostic-status.html +7 -0
- package/dist/patterns/diagram.html +49 -0
- package/dist/patterns/documentation-layout.html +18 -0
- package/dist/patterns/emphasis-budget.html +21 -0
- package/dist/patterns/entry-index.html +16 -0
- package/dist/patterns/evidence-relationship.html +1 -0
- package/dist/patterns/facts.html +7 -0
- package/dist/patterns/fault-banner.html +19 -0
- package/dist/patterns/fault-blocking.html +25 -0
- package/dist/patterns/fault-details.html +11 -0
- package/dist/patterns/fault-inline.html +17 -0
- package/dist/patterns/fault-notification.html +20 -0
- package/dist/patterns/fault-reference.html +5 -0
- package/dist/patterns/fault-summary.html +20 -0
- package/dist/patterns/fault.html +17 -0
- package/dist/patterns/feed-item.html +12 -0
- package/dist/patterns/focus-stage.html +4 -0
- package/dist/patterns/frame.html +4 -0
- package/dist/patterns/freshness.html +1 -0
- package/dist/patterns/handoff-summary.html +1 -0
- package/dist/patterns/hero.html +17 -0
- package/dist/patterns/hierarchy-tree.html +11 -0
- package/dist/patterns/identifier.html +9 -0
- package/dist/patterns/landmark-region.html +4 -0
- package/dist/patterns/lane-board.html +10 -0
- package/dist/patterns/marketing-shell.html +40 -0
- package/dist/patterns/measure.html +4 -0
- package/dist/patterns/metric-value-change.html +9 -0
- package/dist/patterns/mosaic.html +6 -0
- package/dist/patterns/navigation-shell.html +8 -0
- package/dist/patterns/overflow-command-disclosure.html +6 -0
- package/dist/patterns/overview-disclosure.html +12 -0
- package/dist/patterns/path-summary.html +8 -0
- package/dist/patterns/priority-stack.html +4 -0
- package/dist/patterns/progress-bar.html +15 -0
- package/dist/patterns/prose.html +9 -0
- package/dist/patterns/rail.html +4 -0
- package/dist/patterns/recovery-actions.html +5 -0
- package/dist/patterns/relationship-index.html +8 -0
- package/dist/patterns/reorder-states.html +31 -0
- package/dist/patterns/resizable-split-pane.html +11 -0
- package/dist/patterns/responsive-grid.html +5 -0
- package/dist/patterns/scope-trail.html +1 -0
- package/dist/patterns/scroll-progress.html +6 -0
- package/dist/patterns/section-heading.html +12 -0
- package/dist/patterns/security-blockers.html +3 -0
- package/dist/patterns/security-evidence-age.html +1 -0
- package/dist/patterns/security-evidence-chain.html +2 -0
- package/dist/patterns/security-exception.html +2 -0
- package/dist/patterns/security-invariant-result.html +1 -0
- package/dist/patterns/security-posture.html +22 -0
- package/dist/patterns/security-state-matrix.html +5 -0
- package/dist/patterns/security-trend.html +1 -0
- package/dist/patterns/security-unknown.html +2 -0
- package/dist/patterns/sidebar.html +4 -0
- package/dist/patterns/site-footer.html +12 -0
- package/dist/patterns/site-header.html +18 -0
- package/dist/patterns/spatial-canvas.html +13 -0
- package/dist/patterns/spinner.html +4 -0
- package/dist/patterns/split-pane.html +4 -0
- package/dist/patterns/stack.html +5 -0
- package/dist/patterns/state-survivability.html +19 -0
- package/dist/patterns/steps.html +8 -0
- package/dist/patterns/switcher.html +4 -0
- package/dist/patterns/tooltip.html +48 -0
- package/dist/patterns/verification-frame.html +22 -0
- package/dist/patterns/workspace-shell.html +6 -0
- package/dist/tokens.css +436 -1
- package/docs/BRANDING.md +6 -1
- package/docs/MARKETING-SITES.md +321 -0
- package/figma/component-contracts.json +1544 -0
- package/package.json +34 -8
- package/patterns/active-filter-summary.html +10 -0
- package/patterns/aegis-faults.manifest.md +81 -0
- package/patterns/attention-path.html +29 -0
- package/patterns/badge.html +9 -0
- package/patterns/callout.html +23 -0
- package/patterns/card-grid.html +25 -0
- package/patterns/character-grid-3270.html +39 -0
- package/patterns/character-grid-field.html +21 -0
- package/patterns/character-grid-keys.html +20 -0
- package/patterns/character-grid-reveal.html +16 -0
- package/patterns/character-grid-selection.html +30 -0
- package/patterns/character-grid-status.html +11 -0
- package/patterns/character-grid-workflow.html +147 -0
- package/patterns/character-grid.html +16 -0
- package/patterns/cluster.html +5 -0
- package/patterns/code-sample.html +9 -0
- package/patterns/command-group.html +6 -0
- package/patterns/comparison-grid.html +7 -0
- package/patterns/comparison-pairs.html +13 -0
- package/patterns/cta.html +12 -0
- package/patterns/dense-ledger.html +7 -0
- package/patterns/diagnostic-status.html +7 -0
- package/patterns/diagram.html +49 -0
- package/patterns/documentation-layout.html +18 -0
- package/patterns/emphasis-budget.html +21 -0
- package/patterns/entry-index.html +16 -0
- package/patterns/evidence-relationship.html +1 -0
- package/patterns/facts.html +7 -0
- package/patterns/fault-banner.html +19 -0
- package/patterns/fault-blocking.html +25 -0
- package/patterns/fault-details.html +11 -0
- package/patterns/fault-inline.html +17 -0
- package/patterns/fault-notification.html +20 -0
- package/patterns/fault-reference.html +5 -0
- package/patterns/fault-summary.html +20 -0
- package/patterns/fault.html +17 -0
- package/patterns/feed-item.html +12 -0
- package/patterns/focus-stage.html +4 -0
- package/patterns/frame.html +4 -0
- package/patterns/freshness.html +1 -0
- package/patterns/handoff-summary.html +1 -0
- package/patterns/hero.html +17 -0
- package/patterns/hierarchy-tree.html +11 -0
- package/patterns/identifier.html +9 -0
- package/patterns/landmark-region.html +4 -0
- package/patterns/lane-board.html +10 -0
- package/patterns/manifest.md +2 -0
- package/patterns/marketing-shell.html +40 -0
- package/patterns/measure.html +4 -0
- package/patterns/metric-value-change.html +9 -0
- package/patterns/mosaic.html +6 -0
- package/patterns/navigation-shell.html +8 -0
- package/patterns/overflow-command-disclosure.html +6 -0
- package/patterns/overview-disclosure.html +12 -0
- package/patterns/path-summary.html +8 -0
- package/patterns/priority-stack.html +4 -0
- package/patterns/progress-bar.html +15 -0
- package/patterns/prose.html +9 -0
- package/patterns/rail.html +4 -0
- package/patterns/recovery-actions.html +5 -0
- package/patterns/relationship-index.html +8 -0
- package/patterns/reorder-states.html +31 -0
- package/patterns/resizable-split-pane.html +11 -0
- package/patterns/responsive-grid.html +5 -0
- package/patterns/scope-trail.html +1 -0
- package/patterns/scroll-progress.html +6 -0
- package/patterns/section-heading.html +12 -0
- package/patterns/security-blockers.html +3 -0
- package/patterns/security-evidence-age.html +1 -0
- package/patterns/security-evidence-chain.html +2 -0
- package/patterns/security-exception.html +2 -0
- package/patterns/security-invariant-result.html +1 -0
- package/patterns/security-posture.html +22 -0
- package/patterns/security-posture.manifest.md +20 -0
- package/patterns/security-state-matrix.html +5 -0
- package/patterns/security-trend.html +1 -0
- package/patterns/security-unknown.html +2 -0
- package/patterns/sidebar.html +4 -0
- package/patterns/site-footer.html +12 -0
- package/patterns/site-header.html +18 -0
- package/patterns/spatial-canvas.html +13 -0
- package/patterns/spinner.html +4 -0
- package/patterns/split-pane.html +4 -0
- package/patterns/stack.html +5 -0
- package/patterns/state-survivability.html +19 -0
- package/patterns/steps.html +8 -0
- package/patterns/switcher.html +4 -0
- package/patterns/tooltip.html +48 -0
- package/patterns/verification-frame.html +22 -0
- package/patterns/workspace-shell.html +6 -0
- package/schemas/brand-manifest.schema.json +17 -3
- package/tokens/echelon.tokens.json +2801 -0
|
@@ -0,0 +1,321 @@
|
|
|
1
|
+
# Building an Echelon marketing site with Forma
|
|
2
|
+
|
|
3
|
+
This guide is for agents and engineers who create or migrate an Echelon
|
|
4
|
+
marketing site, for example Dokimos, Ordo, Praxis, Limen, Vigila, Tutoris, or
|
|
5
|
+
the main Echelon Foundry site.
|
|
6
|
+
|
|
7
|
+
- Rules: [`requirements/MARKETING-PRESENTATION.md`](../requirements/MARKETING-PRESENTATION.md)
|
|
8
|
+
- Distribution decision: [ADR-0003](decisions/ADR-0003-marketing-presentation-distribution.md)
|
|
9
|
+
- Working reference: [`examples/echelon-marketing-site`](../examples/echelon-marketing-site)
|
|
10
|
+
- Migrating an existing site: [`docs/marketing/MIGRATION-CONTRACT.md`](marketing/MIGRATION-CONTRACT.md)
|
|
11
|
+
|
|
12
|
+
## 1. How do I make a new Echelon marketing site?
|
|
13
|
+
|
|
14
|
+
1. Create `forma.lock` (see question 2) and install the pinned assets.
|
|
15
|
+
2. Start every page from the MarketingShell (`patterns/marketing-shell.html`).
|
|
16
|
+
3. Compose each page from Forma components:
|
|
17
|
+
- hero;
|
|
18
|
+
- section heading;
|
|
19
|
+
- card grid;
|
|
20
|
+
- facts;
|
|
21
|
+
- entry index;
|
|
22
|
+
- steps;
|
|
23
|
+
- badges;
|
|
24
|
+
- CTA;
|
|
25
|
+
- prose;
|
|
26
|
+
- callout;
|
|
27
|
+
- code sample;
|
|
28
|
+
- documentation layout.
|
|
29
|
+
4. Write content, not CSS. Add `site.css` only for what question 5 allows.
|
|
30
|
+
5. Add the checks from question 8 to CI and deploy with question 9.
|
|
31
|
+
|
|
32
|
+
### Minimal new site
|
|
33
|
+
|
|
34
|
+
```text
|
|
35
|
+
my-site/
|
|
36
|
+
forma.lock
|
|
37
|
+
index.html
|
|
38
|
+
site.css # optional; often empty
|
|
39
|
+
.github/workflows/deploy-pages.yml
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
`forma.lock`:
|
|
43
|
+
|
|
44
|
+
```text
|
|
45
|
+
forma 0.3.0
|
|
46
|
+
repository kemiller2002/forma
|
|
47
|
+
destination assets/forma
|
|
48
|
+
asset forma-echelon-marketing.css sha256:<filled in by install.sh --update>
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
`index.html`:
|
|
52
|
+
|
|
53
|
+
```html
|
|
54
|
+
<!doctype html>
|
|
55
|
+
<html lang="en" data-ef-theme="light">
|
|
56
|
+
<head>
|
|
57
|
+
<meta charset="utf-8">
|
|
58
|
+
<meta name="viewport" content="width=device-width, initial-scale=1">
|
|
59
|
+
<title>Product | Echelon Foundry</title>
|
|
60
|
+
<link rel="preconnect" href="https://fonts.googleapis.com">
|
|
61
|
+
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
|
62
|
+
<link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=IBM+Plex+Mono:wght@400;500&family=Manrope:wght@400;500;600;700&family=Newsreader:opsz,wght@6..72,500&display=swap">
|
|
63
|
+
<link rel="stylesheet" href="/assets/forma/forma-echelon-marketing.css">
|
|
64
|
+
</head>
|
|
65
|
+
<body class="ef-site" data-ef-layout="product">
|
|
66
|
+
<a class="ef-skip-link" href="#main-content">Skip to main content</a>
|
|
67
|
+
<header class="ef-site-header">
|
|
68
|
+
<div class="ef-site-header__inner">
|
|
69
|
+
<div class="ef-site-header__identity">
|
|
70
|
+
<a class="ef-site-header__brand" href="/"><span class="ef-site-header__mark" aria-hidden="true">PX</span><span class="ef-site-header__name">Echelon / Product</span></a>
|
|
71
|
+
</div>
|
|
72
|
+
<nav class="ef-site-nav" aria-label="Primary">
|
|
73
|
+
<ul class="ef-site-nav__list">
|
|
74
|
+
<li><a class="ef-site-nav__link" href="/" aria-current="page">Overview</a></li>
|
|
75
|
+
<li><a class="ef-site-nav__link" href="/docs/">Documentation</a></li>
|
|
76
|
+
<li><a class="ef-site-nav__link" data-ef-variant="action" href="/start/">Get started</a></li>
|
|
77
|
+
</ul>
|
|
78
|
+
</nav>
|
|
79
|
+
</div>
|
|
80
|
+
</header>
|
|
81
|
+
<main class="ef-site__main" id="main-content" tabindex="-1">
|
|
82
|
+
<section class="ef-hero" aria-labelledby="hero-title">
|
|
83
|
+
<div class="ef-hero__content">
|
|
84
|
+
<p class="ef-eyebrow">Product</p>
|
|
85
|
+
<h1 class="ef-hero__title" id="hero-title">One clear promise</h1>
|
|
86
|
+
<p class="ef-lead">What it does and for whom.</p>
|
|
87
|
+
<div class="ef-actions"><a class="ef-button" data-ef-variant="primary" href="/start/">Get started</a></div>
|
|
88
|
+
</div>
|
|
89
|
+
</section>
|
|
90
|
+
</main>
|
|
91
|
+
<footer class="ef-site-footer" data-ef-tone="inverse">
|
|
92
|
+
<div class="ef-site-footer__inner">
|
|
93
|
+
<p class="ef-site-footer__note"><span>© 2026 Echelon Foundry</span></p>
|
|
94
|
+
</div>
|
|
95
|
+
</footer>
|
|
96
|
+
</body>
|
|
97
|
+
</html>
|
|
98
|
+
```
|
|
99
|
+
|
|
100
|
+
### Callouts in long-form content
|
|
101
|
+
|
|
102
|
+
Most prose needs no callout. Use `.ef-callout` (`patterns/callout.html`) only when a reader must notice one of four kinds of supporting material:
|
|
103
|
+
|
|
104
|
+
| `data-ef-callout` | Use for | Element |
|
|
105
|
+
|---|---|---|
|
|
106
|
+
| `note` | Context the reader can skip without losing the argument | `aside` |
|
|
107
|
+
| `caution` | A consequence to weigh before acting on the surrounding text | `aside` |
|
|
108
|
+
| `evidence` | Quoted or cited source material, with its source | `figure` holding a `blockquote` and a `figcaption` |
|
|
109
|
+
| `decision` | A settled outcome that later sections refer to | `aside` |
|
|
110
|
+
|
|
111
|
+
Every callout starts with a visible `.ef-callout__label` naming its kind, and the container is named by that label (`aria-labelledby`). The label is the primary cue. Each kind also has its own rule pattern, so kinds stay distinct in grayscale, forced colors and print. Do not use a callout for decoration, pull quotes or ordinary emphasis: use `<strong>`, a `blockquote` or a heading instead. Callouts have no runtime and no state. Static Markdown pipelines can emit the markup directly.
|
|
112
|
+
|
|
113
|
+
## 2. How do I consume Forma?
|
|
114
|
+
|
|
115
|
+
Pin a release. Never copy Forma CSS into the site, and never link Forma `main`
|
|
116
|
+
or the Forma documentation site.
|
|
117
|
+
|
|
118
|
+
```bash
|
|
119
|
+
# once, and on every deliberate upgrade: download, verify against the
|
|
120
|
+
# release checksums, and record each file's sha256 in forma.lock
|
|
121
|
+
curl -fsSLO https://raw.githubusercontent.com/kemiller2002/forma/v0.3.0/actions/install-presentation/install.sh
|
|
122
|
+
bash install.sh --update
|
|
123
|
+
|
|
124
|
+
# every build: install exactly what the lock pins, or fail
|
|
125
|
+
bash install.sh
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
The installer needs only bash, curl, and `sha256sum` or `shasum`. It does not
|
|
129
|
+
need Node, npm, or .NET.
|
|
130
|
+
|
|
131
|
+
- `--source DIR` installs from a local directory, such as a Forma checkout's
|
|
132
|
+
`dist/marketing` or an offline cache.
|
|
133
|
+
- Commit `forma.lock`. Do not commit the installed `assets/forma/` directory:
|
|
134
|
+
add it to `.gitignore`, because the build recreates it.
|
|
135
|
+
|
|
136
|
+
Sites that already use npm may instead depend on
|
|
137
|
+
`@echelon-foundry/design-system` at an exact version and copy
|
|
138
|
+
`node_modules/@echelon-foundry/design-system/dist/marketing/forma-echelon-marketing.css`
|
|
139
|
+
at build time. The lock file is still the recommended record, because it
|
|
140
|
+
carries the checksum.
|
|
141
|
+
|
|
142
|
+
Available assets for each release:
|
|
143
|
+
|
|
144
|
+
| Asset | Use |
|
|
145
|
+
|---|---|
|
|
146
|
+
| `forma-echelon-marketing.css` | Default for Echelon sites: generic layer plus Echelon theme |
|
|
147
|
+
| `forma-marketing.css` + `forma-marketing-theme-echelon.css` | The same content split in two, for sites that load the theme separately |
|
|
148
|
+
| `forma-all.css` | Adds Forma application patterns (data grid, dense ledger, status lozenge, provenance trail); load it instead of `forma-marketing.css` when needed |
|
|
149
|
+
| `forma-marketing.manifest.json`, `forma-marketing.sha256` | Version, sizes, sources, checksums |
|
|
150
|
+
|
|
151
|
+
## 3. How do I select the Echelon Marketing Theme?
|
|
152
|
+
|
|
153
|
+
Load `forma-echelon-marketing.css`; it already contains the theme. On `<html>`:
|
|
154
|
+
|
|
155
|
+
- Set `data-ef-theme="light"` to match the reference site, which is light
|
|
156
|
+
only.
|
|
157
|
+
- Set `data-ef-theme="dark"` for the validated dark map.
|
|
158
|
+
- Omit the attribute to follow the operating-system preference.
|
|
159
|
+
|
|
160
|
+
For product identity, retarget only the identity tokens, and only to other
|
|
161
|
+
Forma tokens:
|
|
162
|
+
|
|
163
|
+
```css
|
|
164
|
+
/* site.css */
|
|
165
|
+
:root {
|
|
166
|
+
--ef-color-accent-primary: var(--ef-color-accent-secondary);
|
|
167
|
+
--ef-color-accent-hover: var(--ef-color-text-primary);
|
|
168
|
+
}
|
|
169
|
+
```
|
|
170
|
+
|
|
171
|
+
A product that needs its own validated palette gets a brand manifest in Forma
|
|
172
|
+
(`brands/<product>.brand.json`), including the optional extended roles.
|
|
173
|
+
Apply it with `data-ef-brand="<product>"`. The BrandCompiler rejects any role
|
|
174
|
+
pair below its contrast floor.
|
|
175
|
+
|
|
176
|
+
## 4. How do I use the Marketing Shell?
|
|
177
|
+
|
|
178
|
+
`.ef-site` on `<body>` is the shell. Its structure is fixed and appears in
|
|
179
|
+
this order:
|
|
180
|
+
|
|
181
|
+
1. `.ef-skip-link`: first element in `<body>`, targeting `#main-content`.
|
|
182
|
+
2. `header.ef-site-header` > `.ef-site-header__inner`, containing:
|
|
183
|
+
- `.ef-site-header__identity`: brand link with `__mark` (`aria-hidden`)
|
|
184
|
+
and `__name`, plus an optional `__tagline`;
|
|
185
|
+
- `nav.ef-site-nav[aria-label="Primary"]` > `ul.ef-site-nav__list` >
|
|
186
|
+
`a.ef-site-nav__link`. Mark exactly one link `aria-current="page"`. At
|
|
187
|
+
most one link uses `data-ef-variant="action"`.
|
|
188
|
+
3. `main.ef-site__main#main-content[tabindex="-1"]`, which holds:
|
|
189
|
+
- `section.ef-hero` first;
|
|
190
|
+
- `section.ef-section` regions;
|
|
191
|
+
- `.ef-cta`.
|
|
192
|
+
4. `footer.ef-site-footer[data-ef-tone="inverse"]` > `.ef-site-footer__inner`.
|
|
193
|
+
|
|
194
|
+
Page layouts compose inside `main`:
|
|
195
|
+
|
|
196
|
+
- **Marketing page**: hero → sections → CTA. Specimen: `index.html`.
|
|
197
|
+
- **Product page**: hero with status badges and facts → capability card grid
|
|
198
|
+
→ install steps with a code sample → CTA. Specimen: `product.html`.
|
|
199
|
+
- **Documentation page**: `.ef-doc` with `__nav`, `__content` (with
|
|
200
|
+
`.ef-prose`), and optional `__aside`. Specimen: `docs.html`.
|
|
201
|
+
|
|
202
|
+
Set `data-ef-layout="marketing|product|documentation"` on `.ef-site` to
|
|
203
|
+
declare the page type.
|
|
204
|
+
|
|
205
|
+
Surfaces use `data-ef-tone="surface|elevated|inverse"`. Text, link, label,
|
|
206
|
+
and rule colors adapt to the tone automatically. Use one
|
|
207
|
+
`data-ef-variant="primary"` action per hero, section, or CTA.
|
|
208
|
+
|
|
209
|
+
## 5. What belongs in local CSS?
|
|
210
|
+
|
|
211
|
+
Only the following:
|
|
212
|
+
|
|
213
|
+
- identity imagery, such as illustrations or a product mark image;
|
|
214
|
+
- presentation unique to the site's content, such as charts, diagrams,
|
|
215
|
+
interactive demos, and bespoke figures;
|
|
216
|
+
- identity retargets from the allowlist (question 3);
|
|
217
|
+
- experiments pending promotion, each preceded by
|
|
218
|
+
`/* forma-exception: GAP-MKT-xx or issue URL */`.
|
|
219
|
+
|
|
220
|
+
Keep local class names out of the `ef-` namespace. Use a site prefix such as
|
|
221
|
+
`dk-` or `site-`.
|
|
222
|
+
|
|
223
|
+
## 6. What must go back into Forma?
|
|
224
|
+
|
|
225
|
+
Anything another Echelon site could use, and anything that would otherwise
|
|
226
|
+
redefine:
|
|
227
|
+
|
|
228
|
+
- global typography, containers, or the spacing scale;
|
|
229
|
+
- buttons, navigation, cards, or the footer;
|
|
230
|
+
- the responsive system, focus behavior, or section composition.
|
|
231
|
+
|
|
232
|
+
The policy checker rejects these locally. Record the need as a Forma
|
|
233
|
+
capability gap and add it to Forma. Once it is released, upgrade and delete
|
|
234
|
+
the local rule.
|
|
235
|
+
|
|
236
|
+
## 7. How do I upgrade Forma?
|
|
237
|
+
|
|
238
|
+
1. Read the release notes for every version between yours and the target.
|
|
239
|
+
2. Edit `forma.lock` to the new version, then run `bash install.sh --update`.
|
|
240
|
+
The installer verifies the downloads against the release checksums and
|
|
241
|
+
records the new hashes.
|
|
242
|
+
3. Run the site checks (question 8). Review changed patterns you use:
|
|
243
|
+
`patterns/*.html` at the new tag.
|
|
244
|
+
4. Commit `forma.lock`, plus any markup changes the release notes require, as
|
|
245
|
+
one reviewable change.
|
|
246
|
+
|
|
247
|
+
Nothing upgrades automatically. Forma `main` never reaches a site.
|
|
248
|
+
|
|
249
|
+
## 8. How do I test the site before deployment?
|
|
250
|
+
|
|
251
|
+
Run these checks in CI:
|
|
252
|
+
|
|
253
|
+
- **Install:** `bash install.sh`. It fails on any drift.
|
|
254
|
+
- **Local-CSS policy:** use `kemiller2002/forma/actions/check-site-css@v<version>`
|
|
255
|
+
with `files: site.css`, or run
|
|
256
|
+
`dotnet run --project <forma>/tools/SiteCssPolicy/SiteCssPolicy.fsproj -- --forma assets/forma/forma-echelon-marketing.css site.css`.
|
|
257
|
+
- **Structure:** at least the checks in Forma's
|
|
258
|
+
`tests/marketing-structure.test.mjs`:
|
|
259
|
+
- skip link first;
|
|
260
|
+
- one `h1`;
|
|
261
|
+
- no skipped heading levels;
|
|
262
|
+
- one `aria-current` link;
|
|
263
|
+
- at most one primary action per region;
|
|
264
|
+
- only Forma or declared local classes.
|
|
265
|
+
- **Browser:** at 1280, 768, 390, and 320 px, check for:
|
|
266
|
+
- no horizontal overflow;
|
|
267
|
+
- axe WCAG 2.2 A/AA clean;
|
|
268
|
+
- visible keyboard focus;
|
|
269
|
+
- 44px targets.
|
|
270
|
+
|
|
271
|
+
Forma's `tests/browser/marketing.spec.mjs` is the template.
|
|
272
|
+
|
|
273
|
+
## 9. How does GitHub Pages deployment obtain the correct Forma assets?
|
|
274
|
+
|
|
275
|
+
The deploy workflow installs exactly what the lock pins, before the site
|
|
276
|
+
build:
|
|
277
|
+
|
|
278
|
+
```yaml
|
|
279
|
+
jobs:
|
|
280
|
+
build:
|
|
281
|
+
runs-on: ubuntu-latest
|
|
282
|
+
steps:
|
|
283
|
+
- uses: actions/checkout@v4
|
|
284
|
+
- uses: kemiller2002/forma/actions/install-presentation@v0.3.0
|
|
285
|
+
with:
|
|
286
|
+
lock: forma.lock
|
|
287
|
+
- uses: kemiller2002/forma/actions/check-site-css@v0.3.0
|
|
288
|
+
with:
|
|
289
|
+
files: site.css
|
|
290
|
+
- run: ./build.sh # the site's own build; copies assets/forma into the output
|
|
291
|
+
- uses: actions/configure-pages@v5
|
|
292
|
+
- uses: actions/upload-pages-artifact@v3
|
|
293
|
+
with:
|
|
294
|
+
path: dist
|
|
295
|
+
```
|
|
296
|
+
|
|
297
|
+
Keep the `@v<version>` of the Forma actions equal to the version in
|
|
298
|
+
`forma.lock`. The download URL is the immutable release asset
|
|
299
|
+
`https://github.com/kemiller2002/forma/releases/download/v<version>/<asset>`.
|
|
300
|
+
|
|
301
|
+
## 10. How do I propose a new reusable marketing component?
|
|
302
|
+
|
|
303
|
+
1. Check first whether an existing component, tone, variant, or layout can
|
|
304
|
+
already express it:
|
|
305
|
+
- `patterns/`
|
|
306
|
+
- `requirements/COMPONENT-CATALOG.md`
|
|
307
|
+
- `catalog/layouts.json`
|
|
308
|
+
2. Open a Forma issue that describes the relationship it must preserve, not
|
|
309
|
+
just its appearance:
|
|
310
|
+
- which sites need it;
|
|
311
|
+
- narrow-screen behavior;
|
|
312
|
+
- accessibility semantics;
|
|
313
|
+
- Visual Engineering basis.
|
|
314
|
+
3. Add it in Forma:
|
|
315
|
+
- pattern HTML;
|
|
316
|
+
- CSS in `src/marketing/` using role tokens only;
|
|
317
|
+
- metadata in `tools/component-meta.mjs`;
|
|
318
|
+
- tests (structure, browser, axe, 320 px);
|
|
319
|
+
- a gap entry closed in `requirements/MARKETING-PRESENTATION.md`.
|
|
320
|
+
4. Release it. The sites then upgrade (question 7) and remove any local
|
|
321
|
+
stand-in.
|