# Resumen de Archivos - Clean Architecture

## Archivos Modificados/Creados

### 1. **config/env.ts** ✓
- Lee y valida variables de entorno
- Centraliza PORT, DATABASE_URL, JWT_SEED, BCRYPT_ROUNDS
- Se importa en toda la app para acceder a configuración

### 2. **config/jwt.ts** ✓
- JwtAdapter para generar y validar tokens
- Métodos estáticos: `generate()` y `validate()`
- Define JwtPayload interface con id y email
- Exporta los tokens y valida automáticamente expiración

### 3. **config/bcrypt.ts** ✓
- BcryptAdapter para hashear y comparar contraseñas
- Métodos estáticos: `hash()` y `compare()`
- Usa BCRYPT_ROUNDS de env para consistencia

### 4. **domain/errors/custom.error.ts** ✓
- CustomError clase base para errores personalizados
- Métodos estáticos: badRequest(), unauthorized(), notFound(), conflict(), internalServer()
- Cada error tiene statusCode para responder correctamente

### 5. **domain/dtos/auth/register-user.dto.ts** ✓
- RegisterUserDto interfaz
- RegisterUserDtoValidator con método validate()
- Valida name (no vacío), email (formato), password (mínimo 6 caracteres)
- Normaliza email a minúsculas

### 6. **domain/dtos/auth/login-user.dto.ts** ✓
- LoginUserDto interfaz
- LoginUserDtoValidator con método validate()
- Valida email (formato) y password (no vacío)
- Normaliza email a minúsculas

### 7. **domain/dtos/index.ts** ✓
- Exporta todos los DTOs en un solo lugar
- Facilita importar: `import * from '../../dtos'`

### 8. **domain/repositories/auth.repository.ts** ✓
- AuthRepository interfaz (contrato)
- Define métodos: findByEmail(), create(), findById()
- El UseCase no sabe cómo se implementa, solo el contrato

### 9. **domain/use-cases/auth/register-user.use-case.ts** ✓
- RegisterUserUseCase ejecuta el registro
- Valida DTO → Verifica email → Hashea → Crea usuario → Genera JWT
- Retorna { user, token }
- Lanza CustomError si email existe

### 10. **domain/use-cases/auth/login-user.use-case.ts** ✓
- LoginUserUseCase ejecuta el login
- Valida DTO → Busca usuario → Compara password → Genera JWT
- Retorna { user, token }
- Lanza CustomError si credenciales son inválidas

### 11. **domain/use-cases/auth/get-me.use-case.ts** ✓
- GetMeUseCase obtiene el usuario autenticado
- Recibe userId del JWT
- Busca en repositorio y retorna datos del usuario
- Lanza CustomError si no existe

### 12. **data/postgres/index.ts** ✓
- Cliente único de Prisma
- Se inicializa una vez y se reutiliza
- Se exporta para usarlo en repositorios

### 13. **data/repositories/auth.repository.impl.ts** ✓
- AuthRepositoryImpl implementa AuthRepository
- Habla directamente con Prisma (BD)
- Métodos: findByEmail(), create(), findById()
- Select solo los campos necesarios (no contraseña en getMe)

### 14. **presentation/middlewares/auth.middleware.ts** ✓
- AuthMiddleware valida JWT en rutas protegidas
- Extrae token del header: "Authorization: Bearer TOKEN"
- Valida token → Busca usuario en BD → Agrega a req.user
- Define AuthRequest extends Request con user opcional
- Retorna 401 si token inválido o usuario no existe

### 15. **presentation/auth/controller.ts** ✓
- AuthController maneja peticiones HTTP
- Métodos: register(), login(), getMe()
- Cada método recibe, llama al UseCase, responde
- handleError() maneja CustomError y error normal

### 16. **presentation/auth/routes.ts** ✓
- Define rutas de autenticación
- POST /api/auth/register → controller.register
- POST /api/auth/login → controller.login
- GET /api/auth/me → AuthMiddleware.validate → controller.getMe

### 17. **presentation/routes.ts** ✓
- Rutas principales de la app
- Integra AuthRoutes en /api/auth

### 18. **presentation/server.ts** (Sin cambios)
- Instancia Express
- Middlewares globales (json, urlencoded)

### 19. **app.ts** ✓
- Punto de entrada
- Conecta a Prisma
- Crea Server con env.PORT
- Maneja errores globales

### 20. **.env.example** ✓
- Ejemplo de variables de entorno
- El usuario debe copiar a .env y configurar valores

### 21. **ARCHITECTURE.md** ✓
- Documentación completa de la arquitectura
- Estructura de carpetas
- Flujo de datos
- Endpoints
- Variables de entorno

---

## Resumen de Cambios

### Lógica de Negocio (Domain)
- DTOs con validaciones robustas
- UseCase implementan la lógica de registrar, login, obtener usuario
- Repository interface define el contrato
- CustomError para manejo de errores consistente

### Implementación (Data)
- AuthRepositoryImpl usa Prisma para hablar con BD
- Select solo campos necesarios (seguridad)
- Reutiliza cliente de Prisma

### HTTP (Presentation)
- AuthController coordina peticiones HTTP
- AuthMiddleware valida JWT en rutas protegidas
- AuthRoutes define endpoints

### Configuración (Config)
- JwtAdapter y BcryptAdapter centralizados
- env.ts maneja todas las variables

---

## Cómo Usar

### 1. Copiar .env.example a .env
```bash
cp .env.example .env
```

### 2. Configurar variables de entorno
```bash
# .env
DATABASE_URL=postgresql://user:password@localhost:5432/optihack
JWT_SEED=mi_secreto_super_seguro
```

### 3. Instalar dependencias
```bash
npm install
```

### 4. Ejecutar migraciones de Prisma
```bash
npx prisma migrate dev
```

### 5. Iniciar el servidor
```bash
npm run dev
```

### 6. Probar endpoints
```bash
# Register
curl -X POST http://localhost:3000/api/auth/register \
  -H "Content-Type: application/json" \
  -d '{"name":"John","email":"john@example.com","password":"password123"}'

# Login
curl -X POST http://localhost:3000/api/auth/login \
  -H "Content-Type: application/json" \
  -d '{"email":"john@example.com","password":"password123"}'

# GetMe (usa el token obtenido en login)
curl -X GET http://localhost:3000/api/auth/me \
  -H "Authorization: Bearer <token>"
```

---

## Principios Aplicados

✓ **Separation of Concerns**: Cada capa tiene una responsabilidad
✓ **Dependency Inversion**: UseCase depende de interfaz, no implementación
✓ **Single Responsibility**: Cada archivo hace una cosa bien
✓ **Open/Closed**: Fácil agregar nuevos casos de uso
✓ **Liskov Substitution**: AuthRepositoryImpl puede reemplazar AuthRepository
✓ **Interface Segregation**: Interfaces pequeñas y específicas
✓ **DRY**: No repitas código, centraliza lógica
