diff --git a/.claude/skills/ssr-form-migration/reference/component-cookbook.md b/.claude/skills/ssr-form-migration/reference/component-cookbook.md index dcfcddb1..af778820 100644 --- a/.claude/skills/ssr-form-migration/reference/component-cookbook.md +++ b/.claude/skills/ssr-form-migration/reference/component-cookbook.md @@ -149,3 +149,34 @@ divergence). Scorecard heuristic 1: faked roots → 0. ``` TODO Phase 2: the simple/advanced toggle becomes a `?mode=` re-render (plain form), not a dedicated route. + +--- + +## The Selmer component library (`auto-ap.ssr.components.selmer` / `sc`) — Phase 2-final + +Every shared component the modal renders through is now a thin Clojure wrapper over a +partial under `resources/templates/components/`. **Reuse these before reaching for the +Hiccup `com/*` versions in a migrated modal.** Each wrapper builds a context (reusing the +real class helpers so output matches modulo Tailwind order) and renders its own partial via +the interop bridge; dynamic HTMX/Alpine attrs go through `sc/attrs->str` → +`{{ attrs|safe }}`. See `selmer-conventions.md` for the mechanics. + +| Wrapper | Partial | Notes | +|---------|---------|-------| +| `sc/hidden` / `sc/text-input` / `sc/money-input` | `hidden`/`text-input`/`money-input`.html | leaf inputs; class via `inputs/default-input-classes` + `use-size` | +| `sc/validated-field` | `validated-field.html` | label + body + always-present error `

`; pass-through attrs land on the wrapping div (the per-row location cell hangs its swap wiring here) | +| `sc/button` / `sc/a-button` / `sc/a-icon-button` | `button`/`a-button`/`a-icon-button`.html | spinner via `{% include "spinner.html" %}`; class via `btn/bg-colors` | +| `sc/badge` / `sc/link` | `badge`/`link`.html | | +| `sc/button-group` / `sc/button-group-button` | `button-group(+button).html` | the group does **not** mutate children's classes (the Hiccup `group-` added rounded-l/r) — add rounding in the caller/template (tabs do) | +| `sc/radio-card` | `radio-card.html` | reproduces the `select-keys [:hx-post :hx-target :hx-swap :hx-include :hx-trigger]` filter (drops `:hx-vals`/`:hx-select`) **and** the dangling-`[:h3]` quirk: only the `