This document provides essential context for AI agents working on the Serika codebase.
- Framework: Next.js (App Router)
- Runtime: Bun
- Language: TypeScript
- Database: PostgreSQL with Prisma ORM
- Authentication: NextAuth.js (shared across all apps)
- Storage Layer: Modular abstraction (
src/lib/storage.ts) supporting S3 (Backblaze B2) and Local Filesystem. - Styling: Tailwind CSS with Framer Motion for animations.
- UI Components: Base UI / Shadcn UI inspired components.
- Rich Text: TipTap (ProseMirror-based) for SerikaDocs editor.
All apps live in one Next.js codebase with subdomain routing via middleware:
- cloud.serika.dev β
src/app/(dashboard)/β SerikaCloud (file storage) - write.serika.dev β
src/app/write/β SerikaDocs (document editor) - mail.serika.dev β
src/app/mail/β SerikaMail (email client) - present.serika.dev β
src/app/present/β SerikaPresent (presentations)
Middleware (src/middleware.ts) detects the subdomain and rewrites URLs internally.
For local dev, use ?app=write / ?app=mail / ?app=present query params, or navigate directly to /write, /mail, /present.
src/components/shared/app-switcher.tsx β grid popover to navigate between apps. Included in every app's sidebar/header.
src/lib/storage.ts: Unified file operations interface. Use instead of direct S3 calls.src/lib/org.ts: Organization helper utilities (role checks, membership queries, ticket numbering).src/lib/audio-metadata.ts: ID3 tags and album art viamusic-metadata-browser.src/app/api/files/: SerikaCloud file management endpoints.src/app/api/docs/: SerikaDocs CRUD endpoints.src/app/api/mail/: SerikaMail endpoints (list, send, aliases, incoming webhook, IMAP credentials).src/app/api/org/: Organization management (CRUD, members, invites, domains, groups, group-mail, tickets).src/app/api/present/: SerikaPresent endpoints (CRUD, slides).src/components/files/: Cloud file browsing and previews.src/components/docs/: TipTap document editor + toolbar.src/components/mail/: Email client UI + compose dialog + org admin + tickets + IMAP settings.src/components/present/: Slide editor, canvas, present mode.
The app supports dual-mode storage controlled by STORAGE_PROVIDER (.env):
- S3 Mode: Uses
@aws-sdk/client-s3. Expects B2 credentials. - Local Mode: Saves files to
LOCAL_STORAGE_PATH(default./storage). Handles recursive directory cleanup and basic range requests.
- Sending: AWS SES v2 (
@aws-sdk/client-sesv2). Credentials viaAWS_SES_*env vars. - Receiving:
POST /api/mail/incomingwebhook β external MTA (Postal/Maddy) delivers here. - Address Setup: Users choose their own
username@serika.proaddress on first visit. No auto-creation. - Aliases: Users can create additional @serika.pro aliases routed to their primary mailbox.
- Folders: Auto-created when mailbox is claimed (inbox, sent, drafts, spam, trash, archive).
- Domain:
MAIL_DOMAINenv var (default:serika.pro).serika.emailis used only for verification emails via SMTP.
- Models: Organization, OrgMember, OrgDomain, OrgInvite, UserGroup, GroupMember, GroupMailbox, GroupMailFolder, GroupEmail, Ticket, TicketMessage, ImapCredential.
- Roles:
OrgRoleenum β OWNER > ADMIN > MEMBER. Role checks viarequireOrgRole()insrc/lib/org.ts. - Custom Domains: Orgs can add custom domains with DNS verification (MX, SPF, DKIM, DMARC). Managed via
/api/org/[orgId]/domains. - Group Mailboxes: Shared inboxes (e.g.
support@acme.com) linked to user groups or org-wide catch-all. Incoming webhook routes to group mailboxes. - Ticketing: Ticket system per org with priorities (URGENT/HIGH/MEDIUM/LOW), statuses (OPEN/IN_PROGRESS/WAITING/RESOLVED/CLOSED), assignment, and internal notes.
- Invites: Token-based invite system with email verification and role assignment.
- IMAP Access: Users generate app passwords via
/api/mail/imapfor external mail clients. Passwords are bcrypt-hashed; plaintext shown once on creation.
- File Keys: Always generated via
generateB2Key(userId, fileName)to ensure uniqueness and user isolation. - Recursive Deletion: Folder deletion MUST be recursive. Use
getDeepFilesto identify all nested assets before purging. - MIME Types: Use
mime-typeslookup for all extraction and upload operations. - Storage Quotas: Always increment/decrement
User.storageUsedin the same transaction or immediate sequence as file operations. - Subdomain Routing: New apps must be added to
SUBDOMAIN_APPSin middleware.ts and get their own route segment.
- Video/Music: Handled via custom players in
FilePreview.tsx. - Images: Direct rendering.
- PDF/Text: Rendered via sandboxed iframes.
- Scaling: Previews use
sm:max-w-4xlfor a spacious feel on desktop.
- BigInt Serialization: Prisma
BigInt(size/storageUsed) must be converted toNumberbefore sending in JSON responses. - Storage Auto-Repair:
/api/usercontains a self-healing bridge that recalculates quotas if they fall out of sync. - MTA Setup Required: SerikaMail receiving requires an external MTA (Postal/Maddy) configured to POST to
/api/mail/incomingwithMAIL_WEBHOOK_SECRETbearer token. - DNS for Subdomains: Coolify needs wildcard or per-app subdomain configuration (cloud/write/mail/present.serika.dev).