generated from coulomb/repo-seed
docs: add specification, reference docs, workplan, and agent guidance
Adds all Phase 0 content that was created but never committed: - CLAUDE.md and SCOPE.md — agent and developer orientation - specs/TailwindForInteractionHubs_v0.2.md — IHF Tailwind coding guide - docs/ — five IHP v1.5 reference guides (overview, data, controllers, realtime, ihf-mapping) - workplans/IHUB-WP-0001 — Phase 1 implementation plan (12 tasks, state-hub synced) Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
289
specs/TailwindForInteractionHubs_v0.2.md
Normal file
289
specs/TailwindForInteractionHubs_v0.2.md
Normal file
@@ -0,0 +1,289 @@
|
||||
# Tailwind for Interaction Hubs
|
||||
|
||||
**Agentic Coding Best-Practice Guide**
|
||||
*For building governed, observable, antifragile hub interfaces with Tailwind + IHP*
|
||||
|
||||
**Version:** 0.2 (Agent-Optimized)
|
||||
**Status:** Production-Ready Reference
|
||||
**Audience:** Human developers **and** coding agents (LLMs)
|
||||
**Framework:** IHP (Integrated Haskell Platform) + Interaction Hub Framework (IHF) layer
|
||||
**Date:** March 2026
|
||||
|
||||
---
|
||||
|
||||
## 0. Quick-Start for Coding Agents (READ THIS FIRST)
|
||||
|
||||
When you receive a UI task for an Interaction Hub:
|
||||
|
||||
1. **Semantic first** — Never start with classes. Ask: “What IHF primitive/widget does this map to?”
|
||||
2. **Import hierarchy** — Always `import Web.View.IHF.Primitives`, `Web.View.IHF.Widgets`, `Web.View.IHF.Classes`.
|
||||
3. **Use wrappers** — Render via `widgetFrame`, `signalBadge`, `hubActionButton`, etc.
|
||||
4. **Token roles only** — Reference `surfaceBase`, `signalSuccess`, `focusRing` (defined in `Theme.hs`).
|
||||
5. **No raw soup** — If you see >8 utility classes in one element, extract to a helper.
|
||||
6. **Document for reproducibility** — Every new primitive gets Haddock + example HSX.
|
||||
|
||||
This guide is your single source of truth. Follow it → zero drift.
|
||||
|
||||
---
|
||||
|
||||
## 1. Purpose
|
||||
|
||||
This guide makes **Tailwind the shared visual grammar** for all Interaction Hubs built on IHP + IHF, while keeping the **IHF semantic model** (Widget, Panel, SignalBadge, etc.) as the architectural control point.
|
||||
|
||||
It guarantees:
|
||||
- Perfect visual coherence across hubs
|
||||
- Zero CSS entropy
|
||||
- Agent-reproducible styling (no folklore)
|
||||
- Governed evolution via semantic contracts
|
||||
- Full compatibility with IHP’s server-rendered HSX, partial updates, and future islands
|
||||
|
||||
**Tailwind is the substrate. IHF widgets are the product.**
|
||||
|
||||
---
|
||||
|
||||
## 2. Core Principle (Agent Rule #1)
|
||||
|
||||
```hs
|
||||
-- ALWAYS do this
|
||||
widgetFrame widget content
|
||||
|
||||
-- NEVER do this
|
||||
<div class="rounded-xl border border-slate-700 bg-slate-900/80 px-4 py-3 shadow-sm ...">
|
||||
```
|
||||
|
||||
**Architecture layers (enforced order):**
|
||||
|
||||
1. **IHF Semantic Model** (`Widget`, `HubPanel`, `CommentThread`…)
|
||||
2. **Visual Primitive Contracts** (`Primitives.hs`)
|
||||
3. **Tailwind Token Application** (centralized in `Classes.hs` + `tailwind.config.js`)
|
||||
4. **Screen Composition**
|
||||
|
||||
---
|
||||
|
||||
## 3. IHP + Tailwind Setup (Mandatory Baseline)
|
||||
|
||||
Follow the official IHP Tailwind guide, then apply these IHF extensions:
|
||||
|
||||
### Required Files (exact locations)
|
||||
|
||||
```text
|
||||
Project Root
|
||||
├── tailwind/
|
||||
│ ├── tailwind.config.js ← extend with IHF tokens
|
||||
│ └── app.css
|
||||
├── Web/View/IHF/
|
||||
│ ├── Theme.hs ← semantic roles
|
||||
│ ├── Tokens.hs ← spacing/radius/shadow maps
|
||||
│ ├── Classes.hs ← reusable class builders
|
||||
│ ├── Primitives.hs ← surface, panel, badge, button…
|
||||
│ ├── Widgets.hs ← widgetFrame, inspectorPanel…
|
||||
│ ├── Patterns.hs ← triageDashboard, decisionBoard…
|
||||
│ ├── AnnotationUI.hs
|
||||
│ └── GovernanceUI.hs
|
||||
├── Web/View/CustomCSSFramework.hs ← IHP component override (required for JIT)
|
||||
└── Config/Config.hs ← option customTailwind
|
||||
```
|
||||
|
||||
**Key tailwind.config.js snippet (add to IHF theme):**
|
||||
|
||||
```js
|
||||
theme: {
|
||||
extend: {
|
||||
colors: {
|
||||
surfaceBase: "hsl(var(--surface-base))",
|
||||
signalSuccess: "hsl(var(--signal-success))",
|
||||
// … all roles from Theme.hs
|
||||
},
|
||||
spacing: { /* baseline rhythm */ },
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**CustomCSSFramework.hs** must expose `customTailwind` with Tailwind classes for all IHP form/button/flash helpers.
|
||||
|
||||
---
|
||||
|
||||
## 4. Recommended Layer Model (Agent Reference)
|
||||
|
||||
| Layer | Name | Lives In | Example Functions | Purpose |
|
||||
|-------|-----------------------------|-------------------|---------------------------------------|---------|
|
||||
| A | Semantic Interaction | Widgets.hs / Types | `widgetFrame`, `commentRail` | What it *is* |
|
||||
| B | Visual Primitive | Primitives.hs | `panel`, `signalBadge`, `actionButton` | Reusable building blocks |
|
||||
| C | Tailwind Utility Application| Classes.hs | `panelClasses`, `badgeVariant` | Actual classes |
|
||||
| D | Screen Composition | Patterns.hs | `triageDashboard` | Workflow views |
|
||||
|
||||
---
|
||||
|
||||
## 5. Golden Rules for Agents
|
||||
|
||||
- **Rule 1**: Every visual element must have a named Haskell wrapper (no raw `<div class="…">` longer than one line).
|
||||
- **Rule 2**: All color/spacing decisions go through `Theme.hs` roles.
|
||||
- **Rule 3**: Variant logic must be exhaustive and named (`primary | ghost | danger`).
|
||||
- **Rule 4**: Commentability is first-class — every widget primitive exposes `commentable :: Bool`.
|
||||
- **Rule 5**: Before writing any new class string, check `Classes.hs`. If missing, add it there with documentation.
|
||||
|
||||
---
|
||||
|
||||
## 6. Visual Language & Tokens (Copy-Paste Ready)
|
||||
|
||||
### 6.1 Color Roles (Theme.hs)
|
||||
|
||||
```hs
|
||||
surfaceBase, surfaceRaised, surfaceMuted,
|
||||
borderSubtle, borderStrong,
|
||||
textPrimary, textSecondary, textMuted,
|
||||
signalInfo, signalSuccess, signalWarning, signalDanger,
|
||||
focusRing, commentAccent, policyAccent, outcomeAccent
|
||||
```
|
||||
|
||||
Map these to CSS variables in `tailwind/app.css` `@layer base`.
|
||||
|
||||
### 6.2 Spacing Rhythm (Tokens.hs)
|
||||
|
||||
```hs
|
||||
space1, space2, space3, space4, space6, space8, space12, space16
|
||||
```
|
||||
|
||||
Use only these. Arbitrary values are forbidden.
|
||||
|
||||
### 6.3 Radius & Shadow
|
||||
|
||||
```hs
|
||||
roundedPanel = "rounded-xl"
|
||||
roundedBadge = "rounded-lg"
|
||||
shadowLight = "shadow-sm"
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 7. Core Primitives (Primitives.hs — Starter Template)
|
||||
|
||||
```hs
|
||||
-- Example: panel
|
||||
panel :: [Attribute] -> Html -> Html
|
||||
panel attrs content = div!
|
||||
( [ class_ (panelClasses <> " " <> unwords (map renderAttr attrs))
|
||||
, role_ "region"
|
||||
] )
|
||||
content
|
||||
|
||||
panelClasses :: Text
|
||||
panelClasses = "bg-surfaceBase border border-borderSubtle rounded-xl shadow-sm px-4 py-3"
|
||||
|
||||
-- Example: signalBadge
|
||||
signalBadge :: SignalStatus -> Html
|
||||
signalBadge status = span!
|
||||
[ class_ (badgeVariant status) ]
|
||||
[ text (statusLabel status) ]
|
||||
```
|
||||
|
||||
All primitives follow this exact signature pattern.
|
||||
|
||||
---
|
||||
|
||||
## 8. Widget-Centered Rules (IHF Core)
|
||||
|
||||
Every `Widget` **must** render via `widgetFrame`:
|
||||
|
||||
```hs
|
||||
widgetFrame :: Widget -> (Widget -> Html) -> Html
|
||||
widgetFrame w inner = div!
|
||||
[ class_ widgetFrameClasses
|
||||
, dataAttribute "widget-id" (widgetId w)
|
||||
, dataAttribute "commentable" (show $ isCommentable w)
|
||||
] $ do
|
||||
widgetHeader w
|
||||
inner w
|
||||
widgetFooter w
|
||||
```
|
||||
|
||||
State cues (inspectable, commentable, in-flight) use **one** consistent visual language (header accent + badge + subtle background shift).
|
||||
|
||||
---
|
||||
|
||||
## 9. Agent-Friendly Practices
|
||||
|
||||
### 9.1 Component Creation Protocol (Mandatory)
|
||||
|
||||
When creating a new primitive:
|
||||
|
||||
1. Add to `Primitives.hs` with full Haddock:
|
||||
```hs
|
||||
{-# LANGUAGE OverloadedStrings #-}
|
||||
-- | A governed action button. Variants map to IHF policy levels.
|
||||
actionButton :: ActionVariant -> Text -> Html
|
||||
```
|
||||
2. Define variant type in `Types.hs`.
|
||||
3. Implement class builder in `Classes.hs`.
|
||||
4. Add example usage in `docs/Examples.hs`.
|
||||
5. Update `Short Operational Checklist` (section 26).
|
||||
|
||||
### 9.2 Prompt Template for Future Agents
|
||||
|
||||
> “Generate an IHF widget for X using only primitives from Web.View.IHF. Use semantic roles from Theme.hs. No raw Tailwind soup. Include comment affordance.”
|
||||
|
||||
---
|
||||
|
||||
## 10. Anti-Patterns (Hard-Coded Agent Rejection Rules)
|
||||
|
||||
- Utility soup longer than 6 classes
|
||||
- Screen-local button/panel/badge reinvention
|
||||
- Literal color names in component signatures
|
||||
- Mixed density without system-level justification
|
||||
- Styling logic inside business controllers
|
||||
- Any custom CSS outside `tailwind/app.css` `@layer components`
|
||||
|
||||
---
|
||||
|
||||
## 11. Forms, Tables, Annotations, Governance (IHF-Specific)
|
||||
|
||||
- **Forms**: Use `styledFormGroupClass` from `CustomCSSFramework.hs` + `fieldWithPolicyNote`.
|
||||
- **Tables**: Standardized `sortableTable` in `Patterns.hs` with actor/timestamp/state columns.
|
||||
- **Annotations**: First-class `annotationThread` + triage variants (`open | reviewed | policySensitive`).
|
||||
- **Governance**: `decisionBanner`, `policyScopeBadge`, `traceabilityChain` — all with built-in comment hooks.
|
||||
|
||||
---
|
||||
|
||||
## 12. File & Module Organization (Exact)
|
||||
|
||||
See section 3. All IHF UI lives under `Web/View/IHF/`.
|
||||
Import graph is strict: `Patterns.hs` → `Widgets.hs` → `Primitives.hs` → `Classes.hs` → `Theme.hs`.
|
||||
|
||||
---
|
||||
|
||||
## 13. Rollout Phases & Minimum Standard
|
||||
|
||||
**Phase 1 (MVP)**: Theme + Tokens + Primitives (panel, button, badge, widgetFrame)
|
||||
**Phase 2**: AnnotationUI + GovernanceUI
|
||||
**Phase 3**: Hub-specific accents + adaptive patterns
|
||||
|
||||
**Every new component** must ship with:
|
||||
- Purpose
|
||||
- Type signature
|
||||
- Allowed variants
|
||||
- Accessibility notes
|
||||
- Commentability behavior
|
||||
- Example HSX
|
||||
|
||||
---
|
||||
|
||||
## 14. Short Operational Checklist (Agent + Human Merge Gate)
|
||||
|
||||
Before any PR/merge:
|
||||
- [ ] Semantic name used
|
||||
- [ ] Imported only from IHF modules
|
||||
- [ ] Classes composed via `Classes.hs`
|
||||
- [ ] State signaling matches existing system
|
||||
- [ ] Focus + contrast + color+icon rule satisfied
|
||||
- [ ] Comment affordance present where applicable
|
||||
- [ ] No custom CSS added
|
||||
- [ ] Agent reproduction test passed (copy-paste into new context works)
|
||||
|
||||
---
|
||||
|
||||
## 15. Motto
|
||||
|
||||
**“Use Tailwind for expression. Let IHF widgets define meaning.”**
|
||||
|
||||
This guide is the contract between humans and agents. Follow it and Interaction Hubs stay coherent, evolvable, and antifragile forever.
|
||||
|
||||
Reference in New Issue
Block a user