Files
jules 11b17b6b6a docs: CLAUDE.md points at LIBS.md; ignore .boot.log
Two follow-ups to 8cd5805:

- CLAUDE.md's "Crema system" section now points at docs/LIBS.md (the
  generated catalog) as the primary lookup. Live manifest reference moved
  below as a fallback. Keeps the LLM's first hit at a compact, alpha-sorted
  table instead of the live JSON.
- The .boot.log file (created by my fresh-clone integration test) was
  accidentally committed in 8cd5805. Remove from tracking and ignore going
  forward.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 18:50:27 +10:00

7.1 KiB

CLAUDE.md

This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.

Hybrid traditional + AI-first webapp built on the Crema design system. This file is a quick map, not a duplication of upstream docs.

Scripts

  • npm run dev — Vite dev server (React Router 7).
  • npm run build — production build (react-router build).
  • npm run start — serve the built app (react-router-serve ./build/server/index.js).
  • npm run typecheckreact-router typegen && tsc. See gotcha below; may crash.
  • start.sh / stop.sh — repo's preferred way to run/stop the dev server in the background.

There is no test runner configured. package.json has no test script and no vitest dep — verify changes by reading code and running the dev server.

App layout (app/)

  • routes/ + routes.ts — file-based React Router 7 routes (Overview, Resources, Activity, Assistant, Library, Settings).
  • components/layout/app-shell.tsx (rail + appbar + avatar dropdown), appbar.tsx, theme-toggle.tsx. Template code, not a lib — fork it freely.
  • components/assistant/message-body.tsx — markdown rendering for assistant replies + action-block pill.
  • components/scripts-dialog.tsx — ⌘⇧P script runner UI.
  • lib/identity.tsuseBrand() / useUser() (default stubs; swap for real session).
  • lib/llm-settings.ts — persisted LLM endpoint + context budget config.
  • lib/page-meta.ts, lib/utils.ts — small helpers.
  • app.css — Tailwind v4 entrypoint; theme @import first, then tailwind, then per-lib @source lines.
  • root.tsxToastProvider + CommandBusProvider wrap point.

What this is

  • React Router 7 + Tailwind v4 SPA.
  • Hybrid traditional + AI-first scaffold. Most surfaces are normal; the Assistant surface is wrapped in <AppShell theme="mightypix"> for the AI-styled mood (warm cream + ink-blue + serif prose).
  • Built on Crema libs (@crema/*-ui) cloned as sibling directories, not npm packages.
  • The @crema/action-bus lib is the foundation: anything (LLM, scripts, WebSocket, tests) can drive the UI via [data-action]-tagged elements. See docs/AI_FIRST.md.

Crema system (authoritative)

  • Lib catalog: see docs/LIBS.md for a snapshot of every @crema/*-ui lib (the ones wired into this project AND the ones available to add). Before building any UI primitive, check there first — there's a good chance a lib already does it. Refresh the snapshot with npm run sync-libs.
  • Each @crema/*-ui lib is its own git repo at https://git.sky-ai.com/CremaUIStudio/lib-<name>-ui, cloned as a sibling of this app. Edits to lib code commit to that lib's repo, not this one.
  • Themes (lib-theme-*) are CSS-only token files at the same Gitea org.
  • Live manifest (which docs/LIBS.md is generated from) is the crema-manifest repo. Gitea's raw-file HTTP URL 404s; clone instead:
    git clone --depth 1 https://git.sky-ai.com/CremaUIStudio/crema-manifest.git /tmp/crema-manifest
    cat /tmp/crema-manifest/manifest.json
    

Adding a lib after scaffold

Prefer the CLI:

crema add <lib-name>      # e.g. crema add status-ui chart-ui

It clones the lib as a sibling, adds the @source line to app/app.css, and wires tsconfig.json paths.

Manual fallback (3 edits):

  1. Clone lib-<name>-ui as a sibling.
  2. app/app.css → add @source "../../lib-<name>-ui/src";
  3. tsconfig.json paths → add "@crema/<name>-ui": ["../lib-<name>-ui/src/index.tsx"] and the /* variant.

Then run npm run sync-libs to refresh docs/LIBS.md.

Theme convention

  • A single theme (lib-theme-mightypix by default) is loaded via :root in app/app.css, first so its embedded @import url(...) Google Fonts declarations resolve to the top of the output.
  • Themes are self-contained: tokens and their font @import url(...) ship inside the theme's CSS file.
  • Per-surface alt themes can be scoped via [data-theme="<name>"] and applied with the shell's theme prop. The Assistant route already does this: <AppShell title="Assistant" theme="mightypix">…</AppShell>.
  • Components reference tokens (var(--card), bg-card, etc.), never hex values. See app/components/layout/THEME_CONTRACT.md for the full token list any theme must implement.
  • Assistant prose uses var(--font-ai-prose). Don't hard-code font families.

Coding conventions

  • lib-*-ui components use inline styles with CSS variables (style={{ background: "var(--card)", color: "var(--foreground)" }}), not Tailwind classes. App routes use Tailwind freely with theme-variable utilities (bg-card, text-muted-foreground).
  • Every shadcn-style component has a [data-slot="..."] attribute — themes target these for surface treatment overrides. Preserve them when editing libs.
  • Lib src/index.tsx files start with // PURPOSE: and // EXPORTS blocks, plus "use client" at the top. Maintain the header.
  • Don't hardcode colors. Use tokens.

Polyrepo gotchas

  • git status at this app's root only shows app changes. To see lib edits, cd ../lib-<name>-ui && git status.
  • Each repo commits and pushes separately.
  • Don't bundle lib edits into app commits.
  • Sibling libs already cloned next to this app include the full Crema set (lib-chat-ui, lib-table-ui, lib-chart-ui, lib-theme-mightypix, etc.) — check ../lib-* before adding anything new.

Marker contract (CLI-managed regions)

This repo was scaffolded from create-crema-app, which patches marker comments. Preserve them when editing:

File Marker
tsconfig.json "// CREMA:PATHS"
app/app.css /* CREMA:SOURCES */
app/routes.ts // CREMA:ROUTES
app/components/layout/app-shell.tsx // CREMA:NAV-ICONS, // CREMA:NAV-ITEMS
app/root.tsx // CREMA:PROVIDERS-IMPORTS, /* CREMA:PROVIDERS-WRAP-OPEN */, /* CREMA:PROVIDERS-WRAP-CLOSE */

Common tasks

  • Run dev: npm run dev
  • Add a UI primitive: check the manifest first; if it exists, crema add <lib>; if not, build inline and consider whether it should become a lib.
  • Add a route: create the file under app/routes/, register in app/routes.ts, add a nav entry in the sidenav (traditional) or chat shell (AI).
  • Switch theme on a route: pass theme="<name>" to <AppShell>. Default (no prop) uses the :root theme.
  • Add a script: drop a .script file into public/scripts/, register it in KNOWN_SCRIPTS in app/components/scripts-dialog.tsx if you want it in the dialog list, or invoke programmatically with runScript("<name>").
  • Make a component scriptable: add data-action="<id>". The bus auto-discovers it.

Known gotchas

  • npm run typecheck may crash with a TypeScript internal error — pre-existing in the Crema toolchain. There's no test runner here, so rely on careful reads + dev server.
  • Vite "Outdated Optimize Dep" 504s after editing vite.config.ts or tsconfig.json: stop dev, rm -rf node_modules/.vite, restart, hard-reload.
  • After editing a sibling lib's exports, the dev server sometimes needs a manual restart to pick up the new types.