# Guia de Despliegue - SmashPoint

Esta guia cubre el proceso completo para desplegar SmashPoint en un entorno de produccion.

## Tabla de Contenidos

1. [Requisitos Previos](#requisitos-previos)
2. [Configuracion del Entorno](#configuracion-del-entorno)
3. [Configuracion de Base de Datos](#configuracion-de-base-de-datos)
4. [Despliegue con PM2](#despliegue-con-pm2)
5. [Configuracion de Nginx](#configuracion-de-nginx)
6. [SSL con Lets Encrypt](#ssl-con-lets-encrypt)
7. [Despliegue con Docker](#despliegue-con-docker)
8. [Monitoreo y Mantenimiento](#monitoreo-y-mantenimiento)

---

## Requisitos Previos

### Software Requerido

| Software | Version | Proposito |
|----------|---------|-----------|
| Node.js | 20.x LTS | Runtime de JavaScript |
| PostgreSQL | 16.x | Base de datos |
| pnpm | 8.15.0+ | Gestor de paquetes |
| Git | 2.x | Control de versiones |
| Nginx | 1.24+ | Servidor web / Proxy inverso |
| PM2 | 5.x | Gestor de procesos (opcional) |
| Docker | 24.x | Contenedores (opcional) |

### Recursos del Servidor

**Minimos:**
- CPU: 2 cores
- RAM: 4 GB
- Disco: 20 GB SSD

**Recomendados:**
- CPU: 4 cores
- RAM: 8 GB
- Disco: 50 GB SSD

---

## Configuracion del Entorno

### 1. Instalar Node.js 20

```bash
# Usando nvm (recomendado)
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.39.0/install.sh | bash
source ~/.bashrc
nvm install 20
nvm use 20
nvm alias default 20

# Verificar instalacion
node --version  # v20.x.x
```

### 2. Instalar pnpm

```bash
npm install -g pnpm
pnpm --version  # 8.x.x
```

### 3. Clonar el Repositorio

```bash
cd /var/www
git clone https://github.com/tu-organizacion/smashpoint.git
cd smashpoint
```

### 4. Configurar Variables de Entorno

```bash
cp apps/web/.env.example apps/web/.env
```

Editar el archivo `.env`:

```env
# Base de datos - Produccion
DATABASE_URL="postgresql://smashpoint_user:PASSWORD_SEGURO@localhost:5432/smashpoint_db?schema=public"

# NextAuth - IMPORTANTE: Generar clave unica
NEXTAUTH_SECRET="$(openssl rand -base64 32)"
NEXTAUTH_URL="https://tudominio.com"

# Aplicacion
NEXT_PUBLIC_APP_URL="https://tudominio.com"
NODE_ENV="production"
```

> **IMPORTANTE:** Nunca usar las credenciales de ejemplo en produccion. Generar una clave secreta unica con `openssl rand -base64 32`.

### 5. Instalar Dependencias

```bash
pnpm install --frozen-lockfile
```

### 6. Construir la Aplicacion

```bash
pnpm build
```

---

## Configuracion de Base de Datos

### 1. Instalar PostgreSQL 16

```bash
# Ubuntu/Debian
sudo sh -c 'echo "deb http://apt.postgresql.org/pub/repos/apt $(lsb_release -cs)-pgdg main" > /etc/apt/sources.list.d/pgdg.list'
wget --quiet -O - https://www.postgresql.org/media/keys/ACCC4CF8.asc | sudo apt-key add -
sudo apt update
sudo apt install postgresql-16

# Iniciar servicio
sudo systemctl start postgresql
sudo systemctl enable postgresql
```

### 2. Crear Base de Datos y Usuario

```bash
sudo -u postgres psql
```

```sql
-- Crear usuario
CREATE USER smashpoint_user WITH PASSWORD 'PASSWORD_SEGURO';

-- Crear base de datos
CREATE DATABASE smashpoint_db OWNER smashpoint_user;

-- Otorgar permisos
GRANT ALL PRIVILEGES ON DATABASE smashpoint_db TO smashpoint_user;

-- Salir
\q
```

### 3. Configurar Conexion Remota (si es necesario)

Editar `/etc/postgresql/16/main/postgresql.conf`:

```conf
listen_addresses = 'localhost'  # o '*' para conexiones remotas
```

Editar `/etc/postgresql/16/main/pg_hba.conf`:

```conf
# Conexion local
local   all   smashpoint_user   md5

# Conexion remota (si es necesario)
host    smashpoint_db   smashpoint_user   192.168.1.0/24   md5
```

Reiniciar PostgreSQL:

```bash
sudo systemctl restart postgresql
```

### 4. Ejecutar Migraciones

```bash
cd /var/www/smashpoint
pnpm db:generate
pnpm db:push
```

### 5. Sembrar Datos Iniciales (Opcional)

```bash
cd apps/web
pnpm db:seed
```

---

## Despliegue con PM2

### 1. Instalar PM2

```bash
npm install -g pm2
```

### 2. Crear Archivo de Configuracion

Crear `ecosystem.config.js` en la raiz del proyecto:

```javascript
module.exports = {
  apps: [
    {
      name: 'smashpoint',
      cwd: '/var/www/smashpoint/apps/web',
      script: 'node_modules/next/dist/bin/next',
      args: 'start',
      instances: 'max',
      exec_mode: 'cluster',
      env: {
        NODE_ENV: 'production',
        PORT: 3000
      },
      env_production: {
        NODE_ENV: 'production',
        PORT: 3000
      },
      // Configuracion de logs
      log_date_format: 'YYYY-MM-DD HH:mm:ss Z',
      error_file: '/var/log/smashpoint/error.log',
      out_file: '/var/log/smashpoint/out.log',
      merge_logs: true,
      // Reinicio automatico
      max_memory_restart: '1G',
      exp_backoff_restart_delay: 100
    }
  ]
};
```

### 3. Crear Directorio de Logs

```bash
sudo mkdir -p /var/log/smashpoint
sudo chown $USER:$USER /var/log/smashpoint
```

### 4. Iniciar la Aplicacion

```bash
pm2 start ecosystem.config.js --env production
```

### 5. Configurar Inicio Automatico

```bash
pm2 startup
pm2 save
```

### 6. Comandos Utiles de PM2

```bash
# Ver estado
pm2 status

# Ver logs
pm2 logs smashpoint

# Reiniciar
pm2 restart smashpoint

# Recargar sin downtime
pm2 reload smashpoint

# Detener
pm2 stop smashpoint

# Monitoreo
pm2 monit
```

---

## Configuracion de Nginx

### 1. Instalar Nginx

```bash
sudo apt install nginx
```

### 2. Crear Configuracion del Sitio

Crear `/etc/nginx/sites-available/smashpoint`:

```nginx
# Redirigir HTTP a HTTPS
server {
    listen 80;
    listen [::]:80;
    server_name tudominio.com www.tudominio.com;

    location / {
        return 301 https://$host$request_uri;
    }

    # Let's Encrypt challenge
    location /.well-known/acme-challenge/ {
        root /var/www/certbot;
    }
}

# Configuracion HTTPS
server {
    listen 443 ssl http2;
    listen [::]:443 ssl http2;
    server_name tudominio.com www.tudominio.com;

    # SSL (sera configurado por Certbot)
    ssl_certificate /etc/letsencrypt/live/tudominio.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/tudominio.com/privkey.pem;
    ssl_session_timeout 1d;
    ssl_session_cache shared:SSL:50m;
    ssl_session_tickets off;

    # Configuracion SSL moderna
    ssl_protocols TLSv1.2 TLSv1.3;
    ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384;
    ssl_prefer_server_ciphers off;

    # HSTS
    add_header Strict-Transport-Security "max-age=63072000" always;

    # Logs
    access_log /var/log/nginx/smashpoint.access.log;
    error_log /var/log/nginx/smashpoint.error.log;

    # Tamano maximo de subida
    client_max_body_size 10M;

    # Gzip
    gzip on;
    gzip_vary on;
    gzip_proxied any;
    gzip_comp_level 6;
    gzip_types text/plain text/css text/xml application/json application/javascript application/rss+xml application/atom+xml image/svg+xml;

    # Proxy a Next.js
    location / {
        proxy_pass http://127.0.0.1:3000;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection 'upgrade';
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_cache_bypass $http_upgrade;
        proxy_read_timeout 86400;
    }

    # Cache para assets estaticos
    location /_next/static {
        proxy_pass http://127.0.0.1:3000;
        proxy_cache_valid 60m;
        add_header Cache-Control "public, immutable";
    }

    # Archivos estaticos
    location /static {
        alias /var/www/smashpoint/apps/web/public;
        expires 30d;
        add_header Cache-Control "public, immutable";
    }
}
```

### 3. Habilitar el Sitio

```bash
sudo ln -s /etc/nginx/sites-available/smashpoint /etc/nginx/sites-enabled/

# Verificar configuracion
sudo nginx -t

# Recargar Nginx
sudo systemctl reload nginx
```

---

## SSL con Lets Encrypt

### 1. Instalar Certbot

```bash
sudo apt install certbot python3-certbot-nginx
```

### 2. Obtener Certificado

```bash
sudo certbot --nginx -d tudominio.com -d www.tudominio.com
```

### 3. Renovacion Automatica

Certbot configura automaticamente la renovacion. Verificar:

```bash
sudo certbot renew --dry-run
```

### 4. Configurar Cron (si es necesario)

```bash
sudo crontab -e
```

Agregar:

```cron
0 12 * * * /usr/bin/certbot renew --quiet
```

---

## Despliegue con Docker

### 1. Archivo docker-compose.yml

El archivo `docker-compose.yml` ya esta incluido en el proyecto. Ubicado en `/root/Padel/docker-compose.yml`.

### 2. Configurar Variables

Crear `.env` en la raiz del proyecto:

```env
POSTGRES_USER=smashpoint_user
POSTGRES_PASSWORD=PASSWORD_SEGURO
POSTGRES_DB=smashpoint_db
DATABASE_URL=postgresql://smashpoint_user:PASSWORD_SEGURO@db:5432/smashpoint_db?schema=public
NEXTAUTH_SECRET=tu-clave-secreta-generada
NEXTAUTH_URL=https://tudominio.com
NEXT_PUBLIC_APP_URL=https://tudominio.com
```

### 3. Construir e Iniciar

```bash
# Construir imagenes
docker compose build

# Iniciar servicios
docker compose up -d

# Ver logs
docker compose logs -f

# Ejecutar migraciones
docker compose exec web pnpm db:push

# Sembrar datos (opcional)
docker compose exec web pnpm db:seed
```

### 4. Comandos Utiles

```bash
# Detener servicios
docker compose down

# Reiniciar
docker compose restart

# Ver estado
docker compose ps

# Acceder al contenedor
docker compose exec web sh

# Backup de base de datos
docker compose exec db pg_dump -U smashpoint_user smashpoint_db > backup.sql
```

---

## Monitoreo y Mantenimiento

### Monitoreo con PM2

```bash
# Dashboard en tiempo real
pm2 monit

# Metricas web (opcional)
pm2 install pm2-server-monit
```

### Backup de Base de Datos

Crear script `/opt/scripts/backup-padel.sh`:

```bash
#!/bin/bash
BACKUP_DIR="/var/backups/smashpoint"
DATE=$(date +%Y%m%d_%H%M%S)
FILENAME="smashpoint_db_$DATE.sql.gz"

mkdir -p $BACKUP_DIR

# Crear backup
pg_dump -U smashpoint_user smashpoint_db | gzip > "$BACKUP_DIR/$FILENAME"

# Eliminar backups antiguos (mantener 7 dias)
find $BACKUP_DIR -name "*.sql.gz" -mtime +7 -delete

echo "Backup completado: $FILENAME"
```

Configurar cron:

```bash
chmod +x /opt/scripts/backup-padel.sh
crontab -e
```

```cron
0 2 * * * /opt/scripts/backup-padel.sh
```

### Actualizaciones

```bash
cd /var/www/smashpoint

# Obtener cambios
git pull origin main

# Instalar dependencias
pnpm install --frozen-lockfile

# Construir
pnpm build

# Ejecutar migraciones (si hay)
pnpm db:push

# Reiniciar aplicacion
pm2 reload smashpoint
```

### Logs

```bash
# Logs de la aplicacion
pm2 logs smashpoint --lines 100

# Logs de Nginx
tail -f /var/log/nginx/smashpoint.error.log

# Logs de PostgreSQL
tail -f /var/log/postgresql/postgresql-16-main.log
```

### Health Check

Crear script `/opt/scripts/health-check.sh`:

```bash
#!/bin/bash
HEALTH_URL="https://tudominio.com/api/health"
RESPONSE=$(curl -s -o /dev/null -w "%{http_code}" $HEALTH_URL)

if [ $RESPONSE != "200" ]; then
    echo "ERROR: Health check failed with status $RESPONSE"
    # Enviar alerta (email, Slack, etc.)
    pm2 restart smashpoint
fi
```

---

## Seguridad

### Firewall (UFW)

```bash
sudo ufw allow ssh
sudo ufw allow 'Nginx Full'
sudo ufw enable
```

### Fail2ban

```bash
sudo apt install fail2ban
sudo systemctl enable fail2ban
```

### Headers de Seguridad

Agregar a la configuracion de Nginx:

```nginx
add_header X-Frame-Options "SAMEORIGIN" always;
add_header X-Content-Type-Options "nosniff" always;
add_header X-XSS-Protection "1; mode=block" always;
add_header Referrer-Policy "strict-origin-when-cross-origin" always;
```

---

## Solucion de Problemas

### La aplicacion no inicia

```bash
# Verificar logs
pm2 logs smashpoint --err

# Verificar puertos
netstat -tlnp | grep 3000

# Verificar conexion a DB
psql -U smashpoint_user -h localhost smashpoint_db -c "SELECT 1"
```

### Error de conexion a base de datos

```bash
# Verificar servicio
sudo systemctl status postgresql

# Verificar logs
tail -f /var/log/postgresql/postgresql-16-main.log

# Probar conexion
psql "postgresql://smashpoint_user:PASSWORD@localhost:5432/smashpoint_db"
```

### Nginx devuelve 502

```bash
# Verificar que la app este corriendo
pm2 status

# Verificar configuracion
sudo nginx -t

# Ver logs
tail -f /var/log/nginx/smashpoint.error.log
```

---

## Checklist de Produccion

- [ ] Variables de entorno configuradas correctamente
- [ ] Base de datos con password seguro
- [ ] NEXTAUTH_SECRET generado de forma segura
- [ ] SSL/HTTPS configurado
- [ ] Firewall configurado
- [ ] Backups automaticos
- [ ] Monitoreo configurado
- [ ] Logs rotados
- [ ] Credenciales por defecto cambiadas
- [ ] Rate limiting configurado
- [ ] Health checks implementados
