Files
crewli/README.md
bert.hausmans 7a69b03c78 chore(docs): drop apps/portal references from load-bearing files
Three load-bearing files still described the pre-WS-3 dual-SPA
reality. Surgical edits to reflect the single-SPA architecture
shipped in WS-3 PR-B (B1: portal moves; B2a: auth+routing
consolidation; B2b: server-side cookie consolidation).

CLAUDE.md:
- Quality-gates ts-reset bullet (line 27): "both SPAs" → "the SPA"
- Quality-gates Vitest bullet (lines 30-32): rewrite from "apps/portal
  has 113+ tests; apps/app currently has no Vitest setup (TECH-APP-VITEST)"
  to current truth: apps/app has Vitest with 213 tests as of PR-B2a.
  TECH-APP-VITEST is implicitly closed.
- Repository layout (line 44): drop apps/portal/ bullet; rephrase
  apps/app/ as the single workspace
- "Apps and portal architecture" → "App architecture": rewrite for
  single-workspace + two access modes. Login-based covers
  organizers + volunteers + crew + super_admin (context-routed
  in-app via useAuthStore.availableContexts); token-based covers
  artists, suppliers, press
- CORS subsection: collapse two-origin config to single origin
  (localhost:5174 dev, https://crewli.app prod). Preserve the
  existing crewli.nl marketing-only note

WS-TOOLING-001 sections (Larastan, Rector, Telescope tooling
configuration) verified untouched via `git diff CLAUDE.md`.

README.md (line 25): collapse the Applications table from two rows
(Organizer + Portal) to one (SPA). Adjust trailing sentence accordingly.

Makefile:
- .PHONY list: drop `portal`
- help echo: drop "make portal" line
- portal target: removed (the underlying `cd apps/portal && pnpm dev`
  would fail since the directory was removed in PR-B1)

Out of scope (deferred to TECH-DOCS-APPS-PORTAL-PURGE backlog item):
.cursor/ instructions, MASTER_PROMPT_*, dev-docs/SETUP, dev-docs/dev-guide,
dev-docs/CLAUDE_CODE_TOOLING. WS-3-SESSION-1C-AUDIT.md skipped (frozen
historical doc).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 00:30:53 +02:00

144 lines
6.0 KiB
Markdown

# Crewli
Multi-tenant SaaS platform for **event and festival operations**: planning, people, accreditation, artist advancing, volunteer shifts, briefings, and show-day tooling (Mission Control). The backend is a **JSON-only** Laravel API; all user interfaces are **Vue 3** single-page apps.
---
## What Crewli covers
- **Organisations & events** — Multi-tenant data with organisation-scoped access; events move through a defined lifecycle (draft → published → registration → buildup → show day → teardown → closed).
- **Festival structure** — Sections, time slots, shifts, assignments, claiming/approval flows for volunteers and crew.
- **People & crowds** — Crowd types (crew, volunteers, artists, guests, press, partners, suppliers), persons, lists, and (planned) rich accreditation (items, zones, hand-out).
- **Artists & advancing** — Booking status, stages/timetable concepts, advance sections and token-based portal access for external artists.
- **Communication** — Briefings, campaigns, and operational messaging (see architecture doc for target modules).
- **Portal (external users)** — One portal app, two modes: **login** (Sanctum) for long-term users such as volunteers, and **token** access for per-event links (e.g. artists, suppliers).
Implementation is phased; the authoritative feature and schema list lives in the architecture and design references below.
---
## Applications
| App | Path | Port | Role |
|-----|------|------|------|
| **SPA** | `apps/app/` | 5174 | Single-SPA product covering **organizers, volunteers, crew, super admins** (context-routed in-app), plus token-based access for artists, suppliers, press. Includes **Platform Admin** section for super admins (`/platform/*`). |
The SPA talks to the API over **CORS** with **Laravel Sanctum** tokens.
---
## Tech stack
| Layer | Technology |
|-------|------------|
| API | PHP 8.2+, Laravel 12, Sanctum, Spatie Permission (and Activity Log / Media Library where used) |
| Data | MySQL 8, Redis (cache/queues) |
| Frontends | Vue 3, TypeScript, Vite, Vuexy + Vuetify, Pinia, TanStack Query, VeeValidate + Zod |
| Local services | Docker Compose (MySQL, Redis, Mailpit) |
**Rule of thumb:** business tables use **ULID** primary keys; event-related data is scoped by **organisation** (global scopes + policies), not ad hoc `where` clauses in controllers.
---
## Project structure
```
crewli/
├── api/ # Laravel 12 REST API (JSON only)
├── apps/
│ ├── app/ # Organizer SPA (primary UI + platform admin)
│ └── portal/ # External portal SPA
├── docker/ # Docker / Compose assets
├── docs/ # SETUP, API notes, schema notes
├── resources/
│ ├── design/ # Product source of truth (design docs, see table below)
│ └── vuexy-admin-*/ # Vuexy template reference (bundled kit)
├── .cursor/ # ARCHITECTURE.md, instructions.md, rules for AI/helpers
└── Makefile # Dev commands
```
Vuexy **`@core/`** and **`@layouts/`** in each app should stay untouched; customize via app config, navigation, and app-level components.
---
## Quick start
```bash
# 1. Infrastructure
make services
# 2. API env, dependencies, database (see docs/SETUP.md)
cd api && cp .env.example .env && composer install && php artisan key:generate && php artisan migrate
# 3. Run API + the SPAs you need (separate terminals)
make api
make app
make portal
```
Detailed setup: **[docs/SETUP.md](docs/SETUP.md)**.
---
## Development URLs
| Service | Development | Env / notes |
|---------|-------------|-------------|
| API | http://localhost:8000/api/v1 | Base path `/api/v1` |
| Organizer | http://localhost:5174 | `FRONTEND_APP_URL` |
| Portal | http://localhost:5175 | `FRONTEND_PORTAL_URL` |
| Mailpit | http://localhost:8025 | Local mail capture |
### Production (crewli.app)
**Domains:** **`crewli.app`** is this product (API + organizer + portal SPAs, transactional email from the app, seeds, etc.). **`crewli.nl`** is reserved for a future **public marketing site** only — do not point this codebase's `APP_URL`, CORS, Sanctum, or app mail at `crewli.nl`.
Typical layout (configure the same values in `api/.env` — see `api/.env.example`):
| Service | URL | Env variable |
|---------|-----|----------------|
| API | `https://api.crewli.app` | `APP_URL` |
| Organizer | `https://crewli.app` | `FRONTEND_APP_URL` |
| Portal | `https://portal.crewli.app` | `FRONTEND_PORTAL_URL` |
Frontends: set `VITE_API_URL=https://api.crewli.app/api/v1` in each app's env for production builds. `SANCTUM_STATEFUL_DOMAINS` must list the **hostnames only** of the two SPAs (e.g. `crewli.app,portal.crewli.app`).
---
## Makefile commands
```bash
make services # MySQL, Redis, Mailpit
make services-stop
make api # Laravel on :8000
make app # Organizer on :5174
make portal # Portal on :5175
make migrate
make fresh # migrate:fresh --seed
make db-shell
```
---
## Documentation
| Resource | Contents |
|----------|----------|
| [resources/design/](resources/design/) | **Canonical product specs** in Markdown. Referenced by `.cursor` and `CLAUDE.md` as source of truth for features and data model: `design-document.md`, `dev-guide.md`, `start-guide.md`. |
| [.cursor/ARCHITECTURE.md](.cursor/ARCHITECTURE.md) | System diagram, apps, multi-tenancy, roles, event lifecycle, API route map, core schema overview (summarises `resources/design` when present) |
| [.cursor/instructions.md](.cursor/instructions.md) | Quick reference, phased roadmap, module build order |
| [.cursor/rules/](.cursor/rules/) | Workspace, Laravel, Vue, testing conventions |
| [docs/SETUP.md](docs/SETUP.md) | Environment and local setup |
| [docs/API.md](docs/API.md) | API notes (if maintained) |
| [docs/SCHEMA.md](docs/SCHEMA.md) | Schema notes (if maintained) |
---
## Testing
```bash
cd api && php artisan test
```
Feature tests should cover happy paths plus **401** (unauthenticated), **403** (wrong organisation), and **422** (validation) where applicable.