⌘J
En esta página 6

Engineering / Setup local

Setup local

Cómo levantar el repo platform de cero (scaffold Laravel + Inertia, tenancy en single-database, un host local) y el gate de calidad local.

Diseño aprobado, aún no implementado. El repo heyaxel/platform existe con sus issues y CI cargados, pero tiene 0 PRs mergeados: esta página describe cómo está planeado el bootstrap (fase F0 del plan de fundación), no un flujo ya corriendo. Los comandos son la intención de diseño, sujeta a ajuste al ejecutar.

El objetivo de F0 es un repo Laravel + Inertia/React corriendo local contra Postgres, listo para meterle dominio, con el gate de calidad enchufado desde el primer commit. Nada de tenancy real todavía (eso es F2): F0 deja el andamio.

Stack pineado

Todo se fija en el repo desde el día 1 para que humano y agentes trabajen sobre las mismas versiones. Nada de “la que tenga instalada la máquina”.

PiezaVersiónDónde se pinea
PHP8.x.tool-versions
Laravel13composer.json
Node20.x.nvmrc / .tool-versions
Gestor JSpnpm (nunca npm)packageManager en package.json
FrontInertia 3 + React 19scaffold Breeze
DBPostgreSQL 18local + Laravel Cloud (Neon)

pnpm, nunca npm. Está declarado en packageManager. Un npm install genera un lockfile ajeno y rompe la reproducibilidad del CI. Ojo con pnpm 10.33 y su default de supply-chain: revisar antes de bumpear.

Bootstrap del repo

Scaffold base

composer create-project + Breeze con preset React deja Laravel + Inertia + React andando con auth de ejemplo.

Tenancy como dependencia

stancl/tenancy se agrega en F0 pero no se configura: solo queda la dependencia. La configuración real (single-database + RLS) es F2.

# 1. Crear el proyecto Laravel
composer create-project laravel/laravel platform
cd platform

# 2. Scaffold Inertia + React (Breeze, preset inertia-react)
composer require laravel/breeze --dev
php artisan breeze:install react

# 3. Front con pnpm (NUNCA npm)
pnpm install

# 4. Agregar la dependencia de tenancy (sin configurar todavía — eso es F2)
composer require stancl/tenancy

El scaffold de dominio (app/Domain/{Labor,Contracts,Signing}/) se organiza por dominio, no por capa: ver Arquitectura. En F0 solo se deja el árbol vacío listo para F2 en adelante.

Postgres local

Una sola base de datos compartida (shared schema): stancl/tenancy va en modo single-database, sin schemas por tenant. Todas las migraciones viven en una carpeta (database/migrations/), no hay migrations/tenant/ separada.

# Con Herd/Valet, Postgres ya corre local. Crear la base:
createdb axel_platform

# .env — conexión local de desarrollo
DB_CONNECTION=pgsql
DB_DATABASE=axel_platform
DB_HOST=127.0.0.1
DB_PORT=5432

php artisan migrate

Development es 100% local (Herd/Valet + Postgres, *.test), costo $0. No hay ambiente cloud de dev: staging vive en Laravel Cloud y se levanta recién en F6.

Un solo host local

Con dominio único (decisión 0.10), el producto resuelve tenants por sesión, no por subdominio. Local alcanza con un host (platform.test): no hacen falta subdominios *.test, wildcard ni entradas por tenant en /etc/hosts.

El staff entra al host, se loguea y elige empresa; a partir de ahí el current_tenant_id de la sesión define el contexto. Los 2 tenants de prueba (acme, contoso) los crea el seeder (F2-05), no un subdominio.

Gate de calidad local

La calidad se valida local antes de pushear, nunca usando el CI como test runner (los repos comparten bolsa de minutos de Actions). Una sola fuente de verdad del pipeline: composer ci:check.

# El pipeline completo, en orden:
composer ci:check
#   1. Wayfinder      → genera artefactos de rutas tipadas
#   2. Pint           → formato de código PHP
#   3. Larastan       → análisis estático (phpstan nivel 7)
#   4. Pest           → suite de tests
#   5. pnpm build     → build del front

El gate local se corre vía bin/ci-local.sh, que verifica versiones pineadas, borra artefactos gitignored y corre ci:check en limpio. Un pre-push hook plano en .githooks/ (sin lefthook) lo dispara antes de cada push.

# Gate local completo antes de pushear
bin/ci-local.sh

Itera con git commit --amend + git push --force-with-lease en vez de apilar push tras push en un PR abierto: cada push es un run de CI nuevo. El workflow lleva concurrency: cancel-in-progress en ramas de PR.

Gate de F0

F0 cierra cuando estas tres cosas pasan a la vez. Sin el gate, no se avanza a F1.

Levanta local

php artisan serve + pnpm dev muestran la página de bienvenida de Breeze.

Tests verdes

php artisan test (Pest) en verde, con el primer test tests/Pest.php corriendo.

El tercer criterio: CI verde en un PR de prueba (un job con composer install

  • pnpm install + Pint + tests + pnpm build). Con eso, la fundación está lista para F1 (auth) y F2 (tenancy). Ver Multi-tenancy para el siguiente escalón.