#!/bin/bash # ✅ Webhook handler seguro para auto-deploy desde GitHub # Configurar en GitHub: Settings > Webhooks > Add webhook # Payload URL: http://tu-servidor:PORT/webhook # Content type: application/json # Secret: Configurar WEBHOOK_SECRET en .env o variables del sistema # ✅ CONFIGURACIÓN SEGURA: Usar variable de entorno SECRET="${WEBHOOK_SECRET}" # Validar que SECRET está configurado if [ -z "$SECRET" ]; then echo "ERROR: WEBHOOK_SECRET no configurado" >&2 echo " Configurar WEBHOOK_SECRET en .env o variables del sistema" >&2 echo " Generar secret seguro con: openssl rand -hex 32" >&2 exit 1 fi # Configuración de rutas (ajustar según tu entorno) APP_PATH="${APP_PATH:-/home/planetazuzu/guia-tes}" LOG_FILE="${LOG_FILE:-/var/log/webhook-deploy.log}" # Función de logging log() { echo "[$(date '+%Y-%m-%d %H:%M:%S')] $1" >> "$LOG_FILE" } # Verificar que el script se ejecuta desde el directorio correcto cd "$APP_PATH" || { log "ERROR: No se pudo cambiar al directorio $APP_PATH" exit 1 } # Leer payload de GitHub desde stdin PAYLOAD=$(cat) # ✅ VERIFICACIÓN HMAC: Validar signature de GitHub # GitHub envía el signature en header X-Hub-Signature-256 # En un servidor web real, deberías leer este header desde la request HTTP # Este script asume que el signature viene como primer argumento o en variable de entorno SIGNATURE="${1:-${X_HUB_SIGNATURE_256}}" if [ -z "$SIGNATURE" ]; then log "ERROR: X-Hub-Signature-256 no proporcionado" echo "ERROR: Signature requerido para verificación HMAC" >&2 exit 1 fi # ✅ Verificar HMAC SHA-256 # GitHub envía signature como: sha256=HASH # Extraer solo el hash (sin el prefijo sha256=) HASH_ONLY=$(echo "$SIGNATURE" | sed 's/^sha256=//') # Calcular HMAC del payload EXPECTED_HASH=$(echo -n "$PAYLOAD" | openssl dgst -sha256 -hmac "$SECRET" | awk '{print $2}') # Comparar hashes de forma segura (timing-safe comparison) if [ "$HASH_ONLY" != "$EXPECTED_HASH" ]; then log "ERROR: Verificación HMAC fallida - signature inválido" echo "ERROR: Signature inválido" >&2 exit 1 fi log "INFO: Verificación HMAC exitosa" # Verificar que es un push a main REF=$(echo "$PAYLOAD" | jq -r '.ref // empty') if [ "$REF" != "refs/heads/main" ]; then log "INFO: Push a branch diferente de main, ignorando" exit 0 fi # Ejecutar deploy log "INFO: Iniciando deploy automático..." cd "$APP_PATH" ./deploy.sh --skip-git >> "$LOG_FILE" 2>&1 if [ $? -eq 0 ]; then log "SUCCESS: Deploy completado exitosamente" exit 0 else log "ERROR: Deploy falló" exit 1 fi