Signage had no agent guidance at all. Add a CLAUDE.md that records the standalone-module architecture, that the parent ROADMAP.md and DESIGN.md are authoritative, the ownership, branding, token, dark-mode, no-native-dialog and plain-language rules, that display pairing is transitional until Stage 1 Settings -> Displays, and the branch-per-PR, no-push-to-main, no-release-tag workflow. The README listed a mobile management UI as out of scope, which contradicts the design contract's responsive requirement; it is a Stage 1 deferral, and now says so alongside how displays work today. Co-Authored-By: Claude Opus 5.5 <[email protected]>
5.1 KiB
CLAUDE.md
Guidance for Claude Code (and other coding agents) working in this repository. It points at
authoritative sources rather than restating them, because restated details drift. Inspect the actual
source, tests, package.json, and CI workflow before relying on anything here or on memory of a
prior session.
What this repository is
Signage is a first-party Ekklesia module in its own repository (Zayin/Signage). It is not part of
the platform monorepo and vendors none of it: it builds against the published @ekklesia/*
module-development packages (platform ADRs 0053 and 0054), ships as one Ekklesia Module Package
(ADR 0049), and reaches PostgreSQL only through the Module Database ABI v1 executor the host hands it
(ADR 0050). Read README.md for what exists and the scope boundaries.
Signage owns its domain: channel groups, audience channels, timelines, slots, signage assignments, playback rules, native images, and its own management and display UI. The platform shell hosts that UI through the generic module loader and never rebuilds it; do not move Signage screens into the platform.
Product direction lives beside this repository
The current roadmap and product/interface design contract are ROADMAP.md and DESIGN.md in the
parent development directory (../ROADMAP.md and ../DESIGN.md in the standard
~/development/ekklesia/ layout). They are deliberately not committed here; do not copy them in.
They are authoritative for product direction. If this repository's documentation disagrees with them,
flag the conflict and correct the repository-local documentation; never silently follow stale text.
Rules from those documents that apply to every change here:
- Shared resources belong to the platform. Displays/devices, identity, branding, mail, storage, and module lifecycle are the platform's. Signage consumes displays; it assigns content to them.
- The current display management is transitional. Signage's viewer roster, display naming, and pairing instructions, together with the platform's sidebar Display devices panel, are what exists today. Stage 1 moves pairing and the one global display name to the platform's Settings → Displays, and Signage then selects an existing display. Fix defects in the current flow, keep existing paired displays, viewer identities, cached content, and assignments working, and do not implement the Stage 1 Settings/Displays architecture early.
- Branding. Normal user-facing UI never hard-codes "Ekklesia" (platform ADR 0046).
- Visual direction. Simple and minimal; responsive; light, dark, and system modes. Normal UI
colours come only from the shared design tokens (
@ekklesia/design-tokens) and shared elements (@ekklesia/ui) — never a hard-coded colour. The display artifact's pure-black stage, blackout, and slate are content presentation, not themed UI. - No browser-native dialogs.
window.alert,window.confirm, andwindow.promptare prohibited. Destructive actions use in-product confirmation proportional to impact: a two-step in-place confirmation for moderate actions, the sharedDialogfor significant ones. - Plain language. Normal church staff must understand the UI without implementation terms; do not expose an internal identifier merely because it exists.
ADRs
docs/architecture/decisions/ holds Signage's own ADRs; the platform's ADRs live in the Ekklesia
repository. Accepted ADRs are immutable except for status and cross-reference corrections. A changed
decision gets a new ADR that supersedes the old one; never rewrite a historical ADR to fit a change.
Working conventions
- Canonical remote:
ssh://[email protected]:2222/Zayin/Signage.git(the platform isZayin/Ekklesia.git). Local clones can be behind:git fetch --prune --tagsand branch fromorigin/main. - One branch per PR off an up-to-date
origin/main. Never push tomain, never merge your own PR, and never create or push a release tag — release tags belong to the human maintainer. - A fix that needs a platform contract change is two PRs: the Ekklesia change first, then Signage, with the compatibility boundary explicit. Do not copy platform logic into Signage to avoid it.
- Every defect fix gets a regression test. Signage never reads the environment, opens its own socket, builds an Ekklesia URL, or applies a migration; all of that reaches it through the host.
Verification
package.json and .gitea/workflows/ci.yml are the source of truth. From a clean checkout:
pnpm install --frozen-lockfile
pnpm lint && pnpm typecheck && pnpm test && pnpm build && pnpm validate
bash ci/check-cleanup.sh
The CI integration job installs the real Module Package into the pinned platform
(ci/platform.env) and drives the Dashboard and a kiosk display in real browsers, running the display
scenarios listed in ci/display-scenarios (bash ci/package.sh, bash ci/fetch-platform.sh,
bash ci/integration.sh; it needs Docker). Unit tests passing is not evidence that a display or
browser behaviour works: verify display behaviour through the integration harness.