You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: skills/multi-tenant-platform/skill.md
+77-2Lines changed: 77 additions & 2 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -51,9 +51,9 @@ These rules apply to every project that uses this skill, regardless of complexit
51
51
52
52
2.**Defense-in-depth isolation.** Never rely on a single layer. Combine: application-level filtering + PostgreSQL RLS + connection-level context (`SET app.tenant_id`). If one layer fails, the others catch it.
53
53
54
-
3.**Semantic tokens only.** UI components never reference raw colors or hardcoded values. All theming goes through semantic design tokens (`--color-surface-primary`, not `--blue-500`).
54
+
3.**Semantic tokens only.** UI components should not reference raw colors or hardcoded values. All theming goes through semantic design tokens (`--color-surface-primary`, not `--blue-500`).
55
55
56
-
4.**Protected tokens.** Certain tokens (accessibility contrast ratios, minimum font sizes, spacing rhythm) are platform-controlled and cannot be overridden by T1 or T2 themes.
56
+
4.**Protected tokens.** Certain tokens (accessibility contrast ratios, minimum font sizes, spacing rhythm) are platform-controlled and cannot be overridden by T1 or T2 themes. This exists for compliance and accessibility: status colors must remain distinguishable for colorblind users, focus indicators must meet WCAG 2.1 requirements, and spacing rhythm must preserve readability. Without protection, a single tenant's brand override could break accessibility for their entire user base.
57
57
58
58
5.**WCAG AA minimum.** All tenant themes must pass WCAG AA contrast checks. The platform enforces this at token generation time, not at runtime.
59
59
@@ -209,6 +209,81 @@ All projects using this skill target:
209
209
210
210
---
211
211
212
+
## Why This Structure
213
+
214
+
The 3-tier model maps to a specific cost structure. Understanding this helps with capacity planning.
215
+
216
+
-**Shared Neon database**: One database project with branch isolation for dev/preview environments. You pay for one database, not one per tenant. Neon branches are copy-on-write, so storage is shared for unchanged data.
217
+
-**Hyperdrive connection pooling**: One Hyperdrive configuration serves all tenants at the edge. Workers reuse pooled TCP connections instead of opening new ones per request. This avoids per-tenant connection overhead.
218
+
-**Single Worker deployment**: One codebase deployed to Cloudflare Workers. Tenant identity is resolved at request time from the hostname or session. There is no per-tenant deployment step.
219
+
-**Token CSS via CDN**: Theme CSS files are static assets served from the edge cache. Switching tenants swaps a CSS import, not a server-side render.
220
+
221
+
The result: infrastructure costs stay roughly flat as tenant count grows. Adding a new T2 tenant is a database row and a DNS record, not a new deployment. The cost scales with traffic and storage, not with tenant count.
222
+
223
+
---
224
+
225
+
## Multi-Domain Tenant Resolution
226
+
227
+
When tenants operate under their own domains (white-label), the platform resolves tenant identity from the incoming request hostname.
228
+
229
+
### Domain Mappings
230
+
231
+
Each tenant can have multiple domains with different roles:
232
+
233
+
```typescript
234
+
// Domain type enum
235
+
typeDomainType='primary'|'alias'|'vanity';
236
+
237
+
// Domain mapping record
238
+
interfaceDomainMapping {
239
+
domain:string; // e.g., "app.clientbrand.com"
240
+
tenant_id:string; // Resolved tenant
241
+
domain_type:DomainType;
242
+
verified:boolean; // DNS ownership confirmed
243
+
ssl_status:string; // Certificate provisioning state
244
+
}
245
+
```
246
+
247
+
| Type | Purpose | Example |
248
+
|------|---------|---------|
249
+
|`primary`| The canonical domain for the tenant |`app.clientbrand.com`|
250
+
|`alias`| Alternative domains that resolve to the same tenant |`clientbrand.example.com`|
251
+
|`vanity`| Short or branded URLs for specific features |`go.clientbrand.com`|
252
+
253
+
### Tenant Resolution Middleware
254
+
255
+
On every incoming request, the Worker resolves the tenant before any application logic runs:
256
+
257
+
1. Extract hostname from the request
258
+
2. Look up `domain_mappings` for a matching, verified domain
259
+
3. If found, set `tenant_id` in the request context
260
+
4. If not found, fall back to the platform's default domain handling (show landing page or 404)
Domain verification uses a DNS TXT record: the tenant adds a `_syncup-verify.domain.com` TXT record containing a platform-issued token. The platform checks this before marking the domain as verified.
278
+
279
+
---
280
+
281
+
## Reporting Issues
282
+
283
+
If RLS policies don't apply as expected or tenant isolation fails during testing, use the `feedback` command to capture the issue for the platform team.
284
+
285
+
---
286
+
212
287
## Related Skills
213
288
214
289
-`theme-inspired-tokens` -- Design token generation and cultural compliance
Cloudflare Hyperdrive provides connection pooling at the edge, eliminating cold-start connection overhead for Neon. This is critical for Workers because:
165
+
Cloudflare Hyperdrive provides connection pooling at the edge, reducing cold-start connection overhead for Neon. This matters for Workers because:
166
166
167
167
- Each Worker invocation would otherwise create a new TCP + TLS connection to Neon.
168
168
- Neon's serverless driver uses WebSocket, but Hyperdrive uses persistent TCP connections from Cloudflare's network.
@@ -176,6 +176,8 @@ Cloudflare Hyperdrive provides connection pooling at the edge, eliminating cold-
176
176
| First query latency | 80-200ms | 10-30ms |
177
177
| Sustained query latency | 20-50ms | 10-30ms |
178
178
179
+
**Cost note**: Neon's free tier supports this branch-based isolation model for development and early production. As tenant count grows, costs scale through connection pooling (Hyperdrive) and storage, not through per-tenant database provisioning. Adding a T2 tenant is a row in the database and an RLS policy, not a new Neon branch.
180
+
179
181
See `templates/hyperdrive-setup.md` for configuration details.
Copy file name to clipboardExpand all lines: skills/theme-inspired-tokens/references/theme-registry.md
+137Lines changed: 137 additions & 0 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -200,6 +200,143 @@ To use a foundation, pass its `id` to the skill: `--theme nihon-no-iro-tradition
200
200
201
201
---
202
202
203
+
### 8. France / International: Art Deco
204
+
205
+
| Field | Value |
206
+
|-------|-------|
207
+
|**ID**|`art-deco-international`|
208
+
|**Name**| Art Deco (Arts Decoratifs) |
209
+
|**Story**| Originating from the 1925 Exposition Internationale des Arts Decoratifs et Industriels Modernes in Paris, Art Deco fused geometric precision with luxury materials. The movement spread globally through architecture (Chrysler Building), fashion (Erté), and graphic design (Cassandre's posters). Its palette combines metallic golds and silvers with deep saturated jewel tones, always arranged in symmetrical, angular compositions. |
210
+
|**Philosophy**| Modernized opulence: machine-age geometry applied to decorative arts. Order and symmetry as expressions of progress. |
211
+
|**Era**| 1920s-1930s, with revival periods in the 1960s and 2010s |
212
+
213
+
**Seed Colors**:
214
+
215
+
| Name | Native | Hex | Provenance |
216
+
|------|--------|-----|------------|
217
+
| Or Champagne | Champagne Gold |`#D4AF37`| The gilded surfaces of Art Deco interiors -- not bright gold but the warm patina of aged brass and gold leaf on plaster reliefs. |
218
+
| Noir Onyx | Onyx Black |`#1A1A1A`| Polished black lacquer, the backdrop for geometric inlays. From Japanese lacquerware adopted by French decorators. |
219
+
| Bleu Saphir | Sapphire Blue |`#0F3B82`| Deep sapphire, the jewel tone of stained glass in Art Deco churches (Sainte-Odile, Paris) and Lalique glasswork. |
220
+
| Vert Jade | Jade Green |`#00786A`| Jade green from the Chinese and Egyptian artifacts that inspired Art Deco's cross-cultural ornament vocabulary. |
221
+
| Ivoire | Ivory |`#F5F0E1`| The warm white of carved ivory inlays in Art Deco furniture by Emile-Jacques Ruhlmann. |
222
+
| Rouille | Rust |`#A0522D`| Oxidized copper and Cor-Ten steel, the warm brown that grounds Deco's metallic palette. |
223
+
224
+
**Suggested Harmony**: Complementary (bold contrasts between jewel tones and metallics)
225
+
226
+
**Radius Tendency**: None to small (sm) -- angular geometry, chamfered corners rather than curves
227
+
228
+
---
229
+
230
+
### 9. Austria: Wiener Werkstatte
231
+
232
+
| Field | Value |
233
+
|-------|-------|
234
+
|**ID**|`wiener-werkstaette`|
235
+
|**Name**| Wiener Werkstatte (Vienna Workshops) |
236
+
|**Story**| Founded in 1903 by Josef Hoffmann and Koloman Moser, the Wiener Werkstatte pursued Gesamtkunstwerk (total work of art) -- designing everything from buildings to teaspoons. The workshop's visual language combined Secessionist flowing lines with a distinctive grid-based ornamental system. Black and white geometric patterns, accented with primary colors, became the workshop's signature through textiles, ceramics, and graphic design. |
237
+
|**Philosophy**| Gesamtkunstwerk: every element of the environment is designed as part of a unified whole. Craft and art are indistinguishable. |
238
+
|**Era**| 1903-1932, Vienna Secession and early Modernism |
239
+
240
+
**Seed Colors**:
241
+
242
+
| Name | Native | Hex | Provenance |
243
+
|------|--------|-----|------------|
244
+
| Schwarz | Black |`#1C1C1C`| The black of Hoffmann's grid patterns and Moser's graphic work. Structural, not decorative. |
245
+
| Weiss | White |`#F4F0E8`| The off-white of Viennese stucco and the Werkstatte's unglazed ceramics. Warm, not clinical. |
246
+
| Schachbrett-Gold | Checkerboard Gold |`#C5A55A`| The gilt surfaces of the Palais Stoclet in Brussels, Hoffmann's most complete Gesamtkunstwerk. |
247
+
| Klimt-Rot | Klimt Red |`#A02C2C`| The warm red of Gustav Klimt's decorative panels, closely associated with the Secession movement. |
248
+
| Silbergrau | Silver Gray |`#8A8A82`| Hammered silver metalwork by Hoffmann -- matte, textured, never polished to a mirror finish. |
249
+
250
+
**Suggested Harmony**: Monochromatic with accent (black/white/gray foundation, selective color accents)
251
+
252
+
**Radius Tendency**: None (strict geometry -- the Hoffmann grid is rectilinear)
253
+
254
+
---
255
+
256
+
### 10. Italy: Milanese Design
257
+
258
+
| Field | Value |
259
+
|-------|-------|
260
+
|**ID**|`milanese-design`|
261
+
|**Name**| Milanese Design (Design Italiano) |
262
+
|**Story**| Milan became the global capital of industrial design in the postwar period through the work of Gio Ponti, Achille Castiglioni, and the studios that supplied Olivetti, Alessi, and Kartell. Italian design balanced engineering precision with playful color and sculptural form. The Compasso d'Oro awards, established in 1954, codified the movement's values: utility, beauty, and production quality as inseparable concerns. |
263
+
|**Philosophy**| Bel design: beauty is not applied to function but emerges from it. Industrial objects deserve the same design attention as fine art. |
264
+
|**Era**| 1950s-1980s, Milan-centered Italian industrial design |
265
+
266
+
**Seed Colors**:
267
+
268
+
| Name | Native | Hex | Provenance |
269
+
|------|--------|-----|------------|
270
+
| Rosso Olivetti | Olivetti Red |`#D43B2E`| The red of the Olivetti Valentine typewriter (1969), designed by Ettore Sottsass. A deliberate break from office-machine gray. |
271
+
| Bianco Carrara | Carrara White |`#F0EDE6`| The warm white of Carrara marble, quarried in Tuscany since Roman times and used in everything from Michelangelo's David to Milanese kitchen countertops. |
272
+
| Grigio Milano | Milan Gray |`#6B6B67`| The concrete and stone gray of Milanese architecture -- restrained, urban, a backdrop for designed objects. |
273
+
| Blu Ponti | Ponti Blue |`#1D5B8E`| The ceramic blue of Gio Ponti's tile work for the Hotel Parco dei Principi in Sorrento (1960). Mediterranean but measured. |
274
+
| Arancione Kartell | Kartell Orange |`#E07028`| The injection-molded plastic orange of Kartell's furniture line -- democratic material, vivid color. |
275
+
| Nero Assoluto | Absolute Black |`#1A1A1E`| The polished granite black of Italian luxury goods -- Brionvega televisions, Artemide lamps. |
276
+
277
+
**Suggested Harmony**: Triadic (bold, saturated palette reflecting Italian design's confidence with color)
278
+
279
+
**Radius Tendency**: Medium (md to lg) -- sculptural, organic curves from Castiglioni's industrial forms
280
+
281
+
---
282
+
283
+
## The Netherlands
284
+
285
+
### 11. De Stijl
286
+
287
+
| Field | Value |
288
+
|-------|-------|
289
+
|**ID**|`de-stijl-movement`|
290
+
|**Name**| De Stijl (The Style) |
291
+
|**Story**| Founded in 1917 by Theo van Doesburg and Piet Mondrian, De Stijl reduced visual language to its most fundamental elements: straight lines, right angles, and three primary colors plus black and white. The movement influenced architecture (Rietveld Schroder House), furniture (Red Blue Chair), and graphic design. Its radical abstraction argued that universal harmony could be expressed through pure geometric relationships. |
292
+
|**Philosophy**| Neoplasticism: universal beauty through the reduction of form to horizontal and vertical lines, and color to the three primaries plus neutrals. |
293
+
|**Era**| 1917-1931, Dutch avant-garde |
294
+
295
+
**Seed Colors**:
296
+
297
+
| Name | Native | Hex | Provenance |
298
+
|------|--------|-----|------------|
299
+
| Mondriaan Rood | Mondrian Red |`#CC1C1C`| The red of Mondrian's Composition paintings -- a specific warm red, slightly darker than fire-engine red, applied in flat, bounded planes. |
300
+
| Mondriaan Blauw | Mondrian Blue |`#1C3D8F`| A deep, slightly warm ultramarine. In Mondrian's compositions, blue planes are typically smaller than red, creating asymmetric visual weight. |
301
+
| Mondriaan Geel | Mondrian Yellow |`#F0C800`| A strong cadmium-adjacent yellow. The lightest primary, often given the largest area in Mondrian's late compositions. |
302
+
| Zwart | Black |`#0A0A0A`| The black of De Stijl's grid lines -- not gray, not softened. The structural element that defines all spatial relationships. |
303
+
| Wit | White |`#F5F5F5`| The white ground of Mondrian's compositions. More area than any single color, white is a compositional element, not empty space. |
304
+
305
+
**Suggested Harmony**: Complementary (primary colors in deliberate tension, as De Stijl intended)
306
+
307
+
**Radius Tendency**: None (strict right angles only -- any curve would violate Neoplastic principles)
308
+
309
+
---
310
+
311
+
## Switzerland (Modern)
312
+
313
+
### 12. Swiss Modernist
314
+
315
+
| Field | Value |
316
+
|-------|-------|
317
+
|**ID**|`swiss-modernist`|
318
+
|**Name**| Swiss Modernist Design |
319
+
|**Story**| Building on the International Typographic Style of the 1950s but extending into the late 20th century, Swiss Modernist design integrated new printing technologies and color systems while maintaining the discipline of the grid. Designers like Wolfgang Weingart (the "father of New Wave typography") and Wim Crouwel pushed Swiss principles toward greater expressiveness while retaining structural rigor. The palette expanded beyond strict black-red-white to include systematic use of color as information. |
320
+
|**Philosophy**| Structured expression: the grid is not a cage but a framework for controlled variation. Precision and personality coexist. |
321
+
|**Era**| 1970s-1990s, evolving from the International Typographic Style |
322
+
323
+
**Seed Colors**:
324
+
325
+
| Name | Native | Hex | Provenance |
326
+
|------|--------|-----|------------|
327
+
| Signalrot | Signal Red |`#E03030`| Derived from Swiss SBB railway signage -- a functional red used for warnings and emphasis. Slightly warmer than the federal flag red. |
328
+
| Nachtschwarz | Night Black |`#181818`| The dense black of offset-printed posters by Weingart and Muller-Brockmann. Ink-dense, not screen-gray. |
329
+
| Papierweiss | Paper White |`#F8F6F0`| The warm white of uncoated Swiss paper stock -- Lessebo, Munken -- with a tactile quality distinct from coated bright white. |
330
+
| Himmelblau | Sky Blue |`#3A7BBF`| Informational blue from Swiss transit maps and wayfinding systems. Functional, high-visibility, paired with white for legibility. |
331
+
| Mittelgrau | Medium Gray |`#717171`| The typographic gray -- the perceived value of a page of body text. A functional neutral. |
332
+
| Signalgelb | Signal Yellow |`#F0C020`| From SBB train livery and Swiss postal branding. A functional accent color for highlighting and warnings. |
333
+
334
+
**Suggested Harmony**: Golden Ratio (systematic color generation within a structured framework)
335
+
336
+
**Radius Tendency**: None to small (sm) -- grid-based geometry with occasional softened corners for interactive elements
337
+
338
+
---
339
+
203
340
## Using Custom Foundations
204
341
205
342
If none of the registered foundations match your project, you can define a custom one. Provide all required fields from the Theme Source layer in `skill.md`:
0 commit comments