#!/bin/bash # Script de mise à jour depuis package tar.gz # Formation Manager Itinova # Ce script met à jour l'application depuis un package tar.gz (sans Git) set -e # Arrêter en cas d'erreur # Couleurs pour les messages GREEN='\033[0;32m' YELLOW='\033[1;33m' RED='\033[0;31m' BLUE='\033[0;34m' NC='\033[0m' # No Color echo "=========================================" echo "Mise à jour Formation Manager Itinova" echo "Depuis package tar.gz" echo "=========================================" echo "" # Vérifier que nous sommes dans le bon répertoire if [ ! -f "package.json" ]; then echo -e "${RED}Erreur: package.json non trouvé.${NC}" echo -e "${RED}Ce script doit être exécuté depuis /var/www/formation-manager-itinova${NC}" exit 1 fi # Vérifier que le fichier .env existe if [ ! -f ".env" ]; then echo -e "${RED}Erreur: fichier .env non trouvé.${NC}" echo -e "${RED}La configuration de l'application est manquante.${NC}" exit 1 fi # Demander le chemin du package echo -e "${BLUE}Veuillez spécifier le chemin complet du package tar.gz :${NC}" read -p "Chemin du package (ex: /tmp/formation-manager-itinova-*.tar.gz): " PACKAGE_PATH if [ ! -f "$PACKAGE_PATH" ]; then echo -e "${RED}Erreur: Le fichier $PACKAGE_PATH n'existe pas.${NC}" exit 1 fi echo "" echo -e "${YELLOW}Package trouvé: $PACKAGE_PATH${NC}" echo "" # Confirmation read -p "Voulez-vous continuer avec la mise à jour ? (oui/non): " CONFIRM if [ "$CONFIRM" != "oui" ]; then echo "Mise à jour annulée." exit 0 fi echo "" echo -e "${YELLOW}1. Sauvegarde de la base de données...${NC}" # Créer un répertoire de backup s'il n'existe pas mkdir -p backups BACKUP_FILE="backups/db-backup-$(date +%Y%m%d-%H%M%S).sql" # Charger les variables d'environnement if [ -f .env ]; then export $(grep -v '^#' .env | xargs) fi # Extraire les informations de connexion depuis DATABASE_URL if [ -z "$DATABASE_URL" ]; then echo -e "${RED}Erreur: DATABASE_URL n'est pas définie dans .env${NC}" exit 1 fi # Parser DATABASE_URL (format: mysql://user:password@host:port/database) DB_USER=$(echo $DATABASE_URL | sed -n 's/.*:\/\/\([^:]*\):.*/\1/p') DB_PASS=$(echo $DATABASE_URL | sed -n 's/.*:\/\/[^:]*:\([^@]*\)@.*/\1/p') DB_HOST=$(echo $DATABASE_URL | sed -n 's/.*@\([^:]*\):.*/\1/p') DB_PORT=$(echo $DATABASE_URL | sed -n 's/.*:\([0-9]*\)\/.*/\1/p') DB_NAME=$(echo $DATABASE_URL | sed -n 's/.*\/\([^?]*\).*/\1/p') echo "Sauvegarde de la base de données $DB_NAME..." mysqldump -h "$DB_HOST" -P "$DB_PORT" -u "$DB_USER" -p"$DB_PASS" "$DB_NAME" --single-transaction --routines --triggers > "$BACKUP_FILE" 2>/dev/null || { echo -e "${YELLOW}Avertissement: Sauvegarde avec privilèges limités${NC}" mysqldump -h "$DB_HOST" -P "$DB_PORT" -u "$DB_USER" -p"$DB_PASS" "$DB_NAME" > "$BACKUP_FILE" 2>/dev/null } if [ -f "$BACKUP_FILE" ] && [ -s "$BACKUP_FILE" ]; then echo -e "${GREEN}✓ Sauvegarde créée: $BACKUP_FILE${NC}" else echo -e "${RED}Erreur: La sauvegarde a échoué${NC}" exit 1 fi echo "" echo -e "${YELLOW}2. Sauvegarde des fichiers actuels...${NC}" BACKUP_DIR="backups/files-backup-$(date +%Y%m%d-%H%M%S)" mkdir -p "$BACKUP_DIR" # Sauvegarder les fichiers importants cp -r client "$BACKUP_DIR/" 2>/dev/null || true cp -r server "$BACKUP_DIR/" 2>/dev/null || true cp -r drizzle "$BACKUP_DIR/" 2>/dev/null || true cp -r shared "$BACKUP_DIR/" 2>/dev/null || true cp package.json "$BACKUP_DIR/" 2>/dev/null || true cp tsconfig.json "$BACKUP_DIR/" 2>/dev/null || true cp vite.config.ts "$BACKUP_DIR/" 2>/dev/null || true echo -e "${GREEN}✓ Fichiers sauvegardés dans: $BACKUP_DIR${NC}" echo "" echo -e "${YELLOW}3. Arrêt du service...${NC}" # Détecter le gestionnaire de processus (systemd ou PM2) if systemctl is-active --quiet formation-manager 2>/dev/null; then echo "Arrêt du service systemd..." sudo systemctl stop formation-manager SERVICE_MANAGER="systemd" echo -e "${GREEN}✓ Service systemd arrêté${NC}" elif pm2 list | grep -q "formation-manager" 2>/dev/null; then echo "Arrêt du processus PM2..." pm2 stop formation-manager SERVICE_MANAGER="pm2" echo -e "${GREEN}✓ Processus PM2 arrêté${NC}" else echo -e "${YELLOW}Aucun service en cours d'exécution détecté${NC}" SERVICE_MANAGER="none" fi echo "" echo -e "${YELLOW}4. Extraction du nouveau code...${NC}" # Créer un répertoire temporaire TEMP_DIR=$(mktemp -d) echo "Extraction dans $TEMP_DIR..." # Extraire le package tar -xzf "$PACKAGE_PATH" -C "$TEMP_DIR" if [ ! -d "$TEMP_DIR/source" ]; then echo -e "${RED}Erreur: Le répertoire 'source' n'a pas été trouvé dans le package${NC}" rm -rf "$TEMP_DIR" exit 1 fi echo -e "${GREEN}✓ Package extrait${NC}" echo "" echo -e "${YELLOW}5. Mise à jour des fichiers...${NC}" # Sauvegarder le fichier .env actuel cp .env .env.backup # Copier les nouveaux fichiers (en excluant certains répertoires) rsync -av --delete \ --exclude='node_modules' \ --exclude='dist' \ --exclude='.env' \ --exclude='.env.backup' \ --exclude='backups' \ --exclude='.manus' \ "$TEMP_DIR/source/" ./ # Restaurer le .env mv .env.backup .env # Nettoyer le répertoire temporaire rm -rf "$TEMP_DIR" echo -e "${GREEN}✓ Fichiers mis à jour${NC}" echo "" echo -e "${YELLOW}6. Installation des dépendances...${NC}" # Vérifier si pnpm est installé if ! command -v pnpm &> /dev/null; then echo -e "${RED}Erreur: pnpm n'est pas installé${NC}" echo "Installation de pnpm..." npm install -g pnpm fi pnpm install echo -e "${GREEN}✓ Dépendances installées${NC}" echo "" echo -e "${YELLOW}7. Application des migrations de base de données...${NC}" # Utiliser drizzle-kit push pour les mises à jour (ne recrée pas les tables existantes) echo "Synchronisation du schéma avec la base de données..." pnpm exec drizzle-kit push || { echo -e "${YELLOW}Avertissement: La synchronisation a échoué, tentative avec generate...${NC}" pnpm exec drizzle-kit generate } echo -e "${GREEN}✓ Schéma de base de données synchronisé${NC}" echo "" echo -e "${YELLOW}8. Compilation du projet...${NC}" pnpm build echo -e "${GREEN}✓ Projet compilé${NC}" echo "" echo -e "${YELLOW}9. Redémarrage du service...${NC}" if [ "$SERVICE_MANAGER" = "systemd" ]; then sudo systemctl start formation-manager sleep 3 if systemctl is-active --quiet formation-manager; then echo -e "${GREEN}✓ Service systemd redémarré avec succès${NC}" else echo -e "${RED}Erreur: Le service n'a pas pu démarrer${NC}" echo "Consultez les logs avec: sudo journalctl -u formation-manager -n 50" exit 1 fi elif [ "$SERVICE_MANAGER" = "pm2" ]; then pm2 start formation-manager echo -e "${GREEN}✓ Processus PM2 redémarré${NC}" else echo -e "${YELLOW}Aucun gestionnaire de service détecté.${NC}" echo -e "${YELLOW}Démarrez manuellement l'application avec: pnpm start${NC}" fi echo "" echo -e "${GREEN}=========================================${NC}" echo -e "${GREEN}Mise à jour terminée avec succès !${NC}" echo -e "${GREEN}=========================================${NC}" echo "" echo "Sauvegardes créées :" echo " - Base de données: $BACKUP_FILE" echo " - Fichiers: $BACKUP_DIR" echo "" echo "Pour vérifier le statut :" if [ "$SERVICE_MANAGER" = "systemd" ]; then echo " sudo systemctl status formation-manager" echo " sudo journalctl -u formation-manager -f" elif [ "$SERVICE_MANAGER" = "pm2" ]; then echo " pm2 status" echo " pm2 logs formation-manager" fi echo ""