# Principles & Guidelines

Operating rules for the Rahhal design system. The same rules apply whether you're a human writing code or an AI agent generating it. The hard rules below are non-negotiable; the audience tracks at the bottom split for humans and agents.

## Hard rules

| rule | what it means |
| --- | --- |
| Compose first | Reach for `@rahhal/ui` before writing your own button. If a wrapper recurs across two or more apps, promote it back into the package. |
| Tokens come from `@rahhal/themes` | Never redefine brand colors in an app's Tailwind config. Edit `packages/themes/src/themes/{light,dark}.ts` and rebuild — never edit `dist/tokens.css` or `dist/tokens.json` by hand. |
| Bilingual + RTL by default | Both `en` and `ar` are supported. Use Tailwind logical utilities (`ms-*`, `me-*`, `ps-*`, `pe-*`, `start-*`, `end-*`) so RTL flips automatically. Locale resolution goes through `@rahhal/i18n` adapters; never hand-roll detection. |
| Auth via `@rahhal/auth` only | Phone OTP is the only sign-in method (standalone OR iOS → web handover). Never import `@supabase/supabase-js` directly. Never parse the URL fragment manually. Never log tokens. |
| Document deliberately | Shared packages get TSDoc on every export, file headers, and a thorough README. Inline comments only when the *why* is non-obvious. |
| No AI attribution in git | Don't add Co-Authored-By Claude (or any AI mention) to commits or PRs. |

## Need a component that isn't here?

The default answer is **not** "build it locally and forget" — it's "plan it for the design system from the start." Follow this flow:

- **Step 1 — search.** Confirm it's really missing. Filter the catalog (`/`) and grep `packages/ui/src`. Variants of existing components (e.g. a button shape) usually belong as a new variant, not a new component.
- **Step 2 — scope.** Will more than one mini-app reasonably use this? If yes, plan it for `@rahhal/ui` from the start. If it's truly one-app-only (e.g. a domain-specific kanban for a single workflow), keep it app-local — but add a comment with the intended promotion trigger.
- **Step 3 — design the public API.** Sketch the props in TypeScript first. Mirror existing conventions: forwardRef, `asChild` where slot composition makes sense, logical utilities for spacing, design-token classes for color.
- **Step 4 — implement under `packages/ui/src/<component>.tsx`.** Add file-level TSDoc. Export from `index.ts`. Add a subpath in `package.json`. The package ships source TSX, not bundled output.
- **Step 5 — add a catalog entry AND a meta row.** `apps/design-system/src/catalog/entries/<slug>.tsx` for the React preview and `apps/design-system/src/spec/components-meta.ts` for the `.md` endpoint. Both are required — a PR shipping UI without updating the catalog is incomplete.
- **Step 6 — open one PR.** Component + tests + catalog entry + meta + i18n strings should land together. Reviewers can verify the docs match the code in a single pass.

> **Takeaway:** the catalog is the public contract. If a component isn't in the catalog, it doesn't exist for the rest of the platform — and that's how features fragment. Build it here, once, well-documented.

## For AI agents

Use this when generating UI for any Rahhal mini-app:

- **Fetch `/skill.md` first** — it lists every catalog page and the cross-platform conventions.
- **Match by token name, not hex.** `bg-primary` is portable across light/dark/RTL; `#C2562B` is not.
- **Read the relevant `/components/<slug>.md` before generating.** It documents props, variants, and gotchas.
- **Honor RTL.** Use logical utilities (`ms-*`, `me-*`, etc.) and the `rtl:rotate-180` modifier on directional icons.
- **Propose new components fully.** When something is missing, deliver source + catalog entry + meta row + i18n strings in one change — don't leave the catalog out of sync.

## For humans

Code-review checklist when shipping platform changes:

- **Catalog updated?** New / renamed components have a `catalog/entries/<slug>.tsx` AND a row in `spec/components-meta.ts`.
- **Themes built?** Token edits are followed by `pnpm --filter @rahhal/themes build` so generated CSS / JSON match.
- **RTL tested?** Flip the locale switcher to AR; logical utilities should mirror the layout without manual flipping.
- **i18n strings present in both locales?** New copy lands in both `en.json` and `ar.json`.
- **TSDoc on shared exports?** Every public symbol in `packages/*` gets a one-line summary, params, and an example for components / hooks.
