This document describes the structure and conventions used in the codebase to keep it maintainable and easy to extend.
app/– Next.js App Router pages and layouts. Keep page components thin; delegate logic to hooks and components.components/– React components.ui/– Reusable primitives (Button, Input, DrawerPanel, FormField, Sonner, etc.). Prefer single responsibility; use design tokens (e.g.text-foreground,border-border,bg-brand-primary) so themes stay consistent.brand/– Brand assets (e.g. Logo).layout/– App shell: header, sidebar, protected-layout, notifications-panel.auth/– Auth guard and invite flows: auth-guard, helper-invite-acceptance.modals/– Dialog-style overlays: ai-rephrase-modal, image-upload-modal, sla-confirmation-modal.drawers/– Side panels: add-helper-drawer, accept-request-drawer, log-time-drawer, end-ticket-drawer, create-sla-drawer.ticket-chat/– Ticket chat feature. All of these use UI primitives where possible.
contexts/– React context providers (user, project selection). Import via@/contextsor@/contexts/user-context.hooks/– Custom hooks for data and behavior (e.g.useTickets,useNotifications). Keep hooks focused and reusable.lib/– Utilities, Supabase client, React Query provider, and shared helpers (e.g.format.ts,utils.ts).types/– Shared TypeScript types (e.g. database types).
-
Reuse over duplicate – Use
@/components/ui/*for buttons, inputs, selects, and the sharedDrawerPanelfor side drawers. Do not add a second Button or inline drawer markup. -
Design tokens – Prefer semantic Tailwind tokens (
foreground,muted-foreground,border,primary) and the custom tokens inapp/globals.css:brand-primary,border-subtle,text-heading,text-muted,bg-subtle,text-tertiary,support-header. Use them as Tailwind classes (e.g.text-brand-primary,bg-support-header). Avoid hardcoding hex in components. -
Single-purpose components – Each component should have one clear responsibility. Split large components or pages into smaller pieces.
-
Context imports – Always use
@/contexts/...(or@/contexts) so paths stay stable regardless of file location. -
Formatting and dates – Use
@/lib/format(e.g.formatRelativeTime) for relative timestamps and shared date formatting. -
Form fields – Use
FormFieldfrom@/components/ui/form-fieldwhen you need a label + control + optional hint; passlabel,id,hint, andchildren(the input/select/textarea).
- Use
DrawerPanelfrom@/components/ui/drawer-panelfor right-side drawers. Passtitle,footer, andchildren; the panel handles backdrop, header with close button, and layout. - For modals, use the existing Dialog from
@/components/ui/dialogor a similar single-purpose wrapper.
- Create the page under
app/and use existing layout (e.g.ProtectedLayout, support layout). - Add data fetching in a hook under
hooks/and use it in the page. - Reuse UI from
components/uiand, when needed, add new UI primitives there so other features can use them.