erp-transportistas-v2/docs/_definitions/DATABASE-SCHEMA.md
Adrian Flores Cortes 3a3eb4089c docs: Propagar templates de documentacion desde erp-core
Estructura _definitions/:
- _INDEX.yml: Indice de catalogos
- MODULES-CATALOG.md: 42 modulos (22 heredados + 20 propios)
- ENTITIES-CATALOG.md: ~153 entities por schema
- SERVICES-CATALOG.md: ~80 services documentados
- DATABASE-SCHEMA.md: 8 schemas con DDL detallado

Estructura _quick/:
- QUICK-INDEX.yml: Navegacion rapida
- QUICK-MODULES.yml: Estado de modulos
- QUICK-DATABASE.yml: Resumen de BD
- QUICK-API.yml: Endpoints principales

Orchestration:
- HERENCIA-ERP-CORE.md: Documentacion de herencia
- directivas/README.md: Directivas locales
- trazas/README.md: Sistema de trazas

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-26 23:07:50 -06:00

364 lines
9.3 KiB
Markdown

# DATABASE-SCHEMA.md - ERP Transportistas
**Version:** 1.0.0
**Fecha:** 2026-01-26
**Engine:** PostgreSQL 15+ con PostGIS
**Total Schemas:** 8 especializados + heredados
**Total Tablas:** ~98 propias + heredadas
---
## Resumen de Schemas
| Schema | Tablas | ENUMs | DDL File | Estado |
|--------|--------|-------|----------|--------|
| transport | ~25 | ~10 | 01-transport-schema-ddl.sql | 100% |
| fleet | ~15 | ~8 | 02-fleet-schema-ddl.sql | 100% |
| tracking | ~10 | ~5 | 03-tracking-schema-ddl.sql | 100% |
| fuel | ~8 | ~4 | 04-fuel-schema-ddl.sql | 100% |
| maintenance | ~12 | ~6 | 05-maintenance-schema-ddl.sql | 100% |
| carriers | ~8 | ~4 | 06-carriers-schema-ddl.sql | 100% |
| billing | ~10 | ~5 | 07-billing-transport-ddl.sql | 100% |
| compliance | ~10 | ~5 | 08-compliance-schema-ddl.sql | 100% |
---
## Schema: transport
### Descripcion
Ordenes de transporte, embarques, viajes y rutas.
### Tablas Principales
```sql
-- Ordenes de Transporte
CREATE TABLE transport.ordenes_transporte (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL REFERENCES auth.tenants(id),
numero VARCHAR(20) NOT NULL,
cliente_id UUID NOT NULL,
status transport.status_ot NOT NULL DEFAULT 'BORRADOR',
fecha_solicitud TIMESTAMPTZ NOT NULL,
fecha_requerida TIMESTAMPTZ,
origen_id UUID NOT NULL,
destino_id UUID NOT NULL,
peso_kg DECIMAL(10,2),
volumen_m3 DECIMAL(10,2),
valor_declarado DECIMAL(12,2),
instrucciones TEXT,
created_at TIMESTAMPTZ DEFAULT NOW(),
updated_at TIMESTAMPTZ DEFAULT NOW()
);
-- Embarques (agrupacion de OTs)
CREATE TABLE transport.embarques (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL,
numero VARCHAR(20) NOT NULL,
viaje_id UUID,
status transport.status_embarque NOT NULL,
created_at TIMESTAMPTZ DEFAULT NOW()
);
-- Viajes
CREATE TABLE transport.viajes (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL,
numero VARCHAR(20) NOT NULL,
unidad_id UUID NOT NULL,
operador_id UUID NOT NULL,
remolque_id UUID,
status transport.status_viaje NOT NULL DEFAULT 'PLANEADO',
fecha_salida_programada TIMESTAMPTZ,
fecha_salida_real TIMESTAMPTZ,
fecha_llegada_programada TIMESTAMPTZ,
fecha_llegada_real TIMESTAMPTZ,
km_inicial INTEGER,
km_final INTEGER,
created_at TIMESTAMPTZ DEFAULT NOW()
);
-- Paradas del viaje
CREATE TABLE transport.paradas_viaje (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
viaje_id UUID NOT NULL REFERENCES transport.viajes(id),
secuencia INTEGER NOT NULL,
tipo transport.tipo_parada NOT NULL, -- ORIGEN, DESTINO, ESCALA
ubicacion_id UUID NOT NULL,
eta TIMESTAMPTZ,
ata TIMESTAMPTZ, -- Actual Time of Arrival
etd TIMESTAMPTZ,
atd TIMESTAMPTZ, -- Actual Time of Departure
status transport.status_parada NOT NULL
);
```
### ENUMs
```sql
CREATE TYPE transport.status_ot AS ENUM (
'BORRADOR', 'CONFIRMADA', 'PLANEADA', 'EN_TRANSITO',
'ENTREGADA', 'FACTURADA', 'CERRADA', 'CANCELADA'
);
CREATE TYPE transport.status_viaje AS ENUM (
'PLANEADO', 'DESPACHADO', 'EN_TRANSITO', 'EN_DESTINO',
'ENTREGADO', 'CERRADO', 'CANCELADO'
);
CREATE TYPE transport.tipo_parada AS ENUM (
'ORIGEN', 'DESTINO', 'ESCALA', 'CRUCE_FRONTERA'
);
```
---
## Schema: fleet
### Descripcion
Unidades, remolques, operadores y documentos.
### Tablas Principales
```sql
-- Unidades (tractoras, cajas)
CREATE TABLE fleet.unidades (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL,
numero_economico VARCHAR(20) NOT NULL,
tipo fleet.tipo_unidad NOT NULL,
marca VARCHAR(50),
modelo VARCHAR(50),
ano INTEGER,
placa VARCHAR(15),
numero_serie VARCHAR(50),
capacidad_kg DECIMAL(10,2),
status fleet.status_unidad NOT NULL DEFAULT 'DISPONIBLE',
km_actual INTEGER,
proximo_servicio_km INTEGER,
created_at TIMESTAMPTZ DEFAULT NOW()
);
-- Operadores
CREATE TABLE fleet.operadores (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL,
numero_empleado VARCHAR(20) NOT NULL,
nombre VARCHAR(100) NOT NULL,
apellido_paterno VARCHAR(50) NOT NULL,
apellido_materno VARCHAR(50),
rfc VARCHAR(13),
curp VARCHAR(18),
licencia_federal VARCHAR(20),
licencia_vencimiento DATE,
status fleet.status_operador NOT NULL DEFAULT 'ACTIVO',
telefono VARCHAR(15),
created_at TIMESTAMPTZ DEFAULT NOW()
);
-- Documentos de unidades
CREATE TABLE fleet.documentos_unidades (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
unidad_id UUID NOT NULL REFERENCES fleet.unidades(id),
tipo fleet.tipo_documento_unidad NOT NULL,
numero VARCHAR(50),
fecha_emision DATE,
fecha_vencimiento DATE,
archivo_url TEXT,
created_at TIMESTAMPTZ DEFAULT NOW()
);
```
### ENUMs
```sql
CREATE TYPE fleet.tipo_unidad AS ENUM (
'TRACTOCAMION', 'RABON', 'TORTON', 'CAJA_SECA',
'CAJA_REFRIGERADA', 'PLATAFORMA', 'LOWBOY', 'TANQUE'
);
CREATE TYPE fleet.status_unidad AS ENUM (
'DISPONIBLE', 'EN_VIAJE', 'EN_MANTENIMIENTO',
'FUERA_SERVICIO', 'BAJA'
);
CREATE TYPE fleet.status_operador AS ENUM (
'ACTIVO', 'EN_VIAJE', 'DESCANSO', 'VACACIONES',
'INCAPACIDAD', 'BAJA'
);
```
---
## Schema: tracking
### Descripcion
Eventos GPS, geocercas, alertas, ETA.
### Tablas Principales
```sql
-- Eventos de tracking
CREATE TABLE tracking.eventos (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL,
unidad_id UUID NOT NULL,
viaje_id UUID,
tipo tracking.tipo_evento NOT NULL,
latitud DECIMAL(10,7) NOT NULL,
longitud DECIMAL(10,7) NOT NULL,
velocidad_kmh INTEGER,
rumbo INTEGER,
odometro INTEGER,
timestamp_gps TIMESTAMPTZ NOT NULL,
timestamp_server TIMESTAMPTZ DEFAULT NOW(),
datos_extra JSONB
);
-- Geocercas
CREATE TABLE tracking.geocercas (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL,
nombre VARCHAR(100) NOT NULL,
tipo tracking.tipo_geocerca NOT NULL,
geometria GEOMETRY(POLYGON, 4326),
radio_metros INTEGER, -- para circulares
activa BOOLEAN DEFAULT true,
created_at TIMESTAMPTZ DEFAULT NOW()
);
-- Alertas
CREATE TABLE tracking.alertas (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL,
viaje_id UUID,
unidad_id UUID,
tipo tracking.tipo_alerta NOT NULL,
severidad tracking.severidad_alerta NOT NULL,
mensaje TEXT NOT NULL,
leida BOOLEAN DEFAULT false,
created_at TIMESTAMPTZ DEFAULT NOW()
);
```
---
## Schema: fuel
### Descripcion
Combustible, peajes, gastos de viaje.
### Tablas Principales
```sql
-- Cargas de combustible
CREATE TABLE fuel.cargas_combustible (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL,
viaje_id UUID,
unidad_id UUID NOT NULL,
operador_id UUID NOT NULL,
estacion VARCHAR(100),
litros DECIMAL(8,2) NOT NULL,
precio_litro DECIMAL(8,4) NOT NULL,
total DECIMAL(10,2) NOT NULL,
odometro INTEGER,
tipo_pago fuel.tipo_pago NOT NULL,
numero_vale VARCHAR(30),
fecha TIMESTAMPTZ NOT NULL,
latitud DECIMAL(10,7),
longitud DECIMAL(10,7),
created_at TIMESTAMPTZ DEFAULT NOW()
);
-- Control de rendimiento
CREATE TABLE fuel.control_rendimiento (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
unidad_id UUID NOT NULL,
periodo_inicio DATE NOT NULL,
periodo_fin DATE NOT NULL,
km_recorridos INTEGER NOT NULL,
litros_consumidos DECIMAL(10,2) NOT NULL,
rendimiento_real DECIMAL(6,2) NOT NULL, -- km/litro
rendimiento_esperado DECIMAL(6,2),
variacion_porcentaje DECIMAL(5,2),
alerta_generada BOOLEAN DEFAULT false
);
```
---
## Schema: compliance
### Descripcion
Carta Porte CFDI 3.1, HOS, inspecciones.
### Tablas Principales
```sql
-- Carta Porte
CREATE TABLE compliance.cartas_porte (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL,
viaje_id UUID NOT NULL,
tipo_cfdi compliance.tipo_cfdi NOT NULL, -- INGRESO, TRASLADO
version_carta_porte VARCHAR(10) DEFAULT '3.1',
uuid_cfdi UUID,
folio_fiscal VARCHAR(50),
fecha_timbrado TIMESTAMPTZ,
status compliance.status_carta_porte NOT NULL,
xml_firmado TEXT,
pdf_url TEXT,
created_at TIMESTAMPTZ DEFAULT NOW()
);
-- Registro HOS (Horas de Servicio)
CREATE TABLE compliance.registros_hos (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL,
operador_id UUID NOT NULL,
fecha DATE NOT NULL,
horas_conduccion DECIMAL(4,2),
horas_servicio DECIMAL(4,2),
horas_descanso DECIMAL(4,2),
status compliance.status_hos NOT NULL,
notas TEXT
);
```
---
## Extensiones Requeridas
```sql
CREATE EXTENSION IF NOT EXISTS "uuid-ossp";
CREATE EXTENSION IF NOT EXISTS "pgcrypto";
CREATE EXTENSION IF NOT EXISTS "postgis"; -- Para tracking geografico
CREATE EXTENSION IF NOT EXISTS "pg_trgm"; -- Para busquedas
```
---
## RLS (Row Level Security)
Todas las tablas implementan RLS por tenant:
```sql
ALTER TABLE transport.ordenes_transporte ENABLE ROW LEVEL SECURITY;
CREATE POLICY tenant_isolation ON transport.ordenes_transporte
USING (tenant_id = current_setting('app.tenant_id')::UUID);
```
---
## Referencias
- DDL completo: `database/ddl/`
- Inventario: `orchestration/inventarios/DATABASE_INVENTORY.yml`
- Entities: `ENTITIES-CATALOG.md`
---
*Ultima actualizacion: 2026-01-26*