VPS Docker -Déploiement sur Ubuntu

Initialisation

Ce guide exhaustif vous accompagne dans la gestion complète de votre application monapplication déployée sur un VPS Ubuntu 24 avec une architecture Docker containerisée. Conçu pour les développeurs et administrateurs système, il couvre tous les aspects de la maintenance, du monitoring, du déploiement et de la sécurité d’une application web moderne.

Technologies couvertes

  • Backend : Laravel 11, PHP 8.2, MySQL 8.0
  • Frontend : React 19, Node.js 20, Bootstrap
  • Infrastructure : Docker, Docker Compose, Traefik
  • CI/CD : GitHub Actions, GitHub Container Registry
  • Monitoring : Health checks, logs centralisés, alertes automatiques

Convention de codage

  • 🇬🇧 English : Commentaires techniques en anglais
  • 🇫🇷 Français : Traductions et explications en français
  • commandes : Formatage des commandes shell
  • Gras : Points importants et concepts clés
  • Citations : Objectifs et notes importantes

Navigation rapide :  – Utilisez Ctrl+F pour rechercher des commandes spécifiques

Table des matières :

Commandes Essentielles

Action Commande
Vérifier les conteneurs docker ps Vérification
Voir les logs docker logs -f [container] Vérification
Redémarrer l’app docker-compose up -d Interaction
Sauvegarder la DB docker exec db mysqldump... Sauvegarde
Déployer docker-compose pull && docker-compose up -d  Déploiement
Nettoyer Docker docker system prune -a Troubleshooting
Surveillance docker stats Monitoring
Accéder au conteneur docker exec -it [container] /bin/bash Vérification

 

Architecture Actuelle

Objectif : Comprendre l’infrastructure de votre application monapplication et identifier les composants critiques de votre stack technique.

Cette section présente l’architecture de votre application containerisée avec 4 services principaux orchestrés par Docker Compose.

Chaque conteneur a un rôle spécifique dans l’écosystème applicatif et communique via un réseau Docker dédié pour garantir la sécurité et les performances.

Conteneurs en cours d’exécution

# Vérifier les conteneurs actifs
docker ps

Résultat attendu :

  • frontend : React 19 (port 80)
  • api : Laravel 11 PHP (ports 80, 9000)
  • db : MySQL 8.0 (ports 3306, 33060)
  • traefik : Reverse Proxy (ports 80, 443)

 

Commandes de Vérification

==> Objectif : Maîtriser les outils de diagnostic et de monitoring pour maintenir la santé de votre application en temps réel.

Ces commandes essentielles vous permettent de surveiller l’état de vos conteneurs, d’analyser les performances système et de diagnostiquer rapidement les problèmes. Elles constituent la base de toute stratégie de monitoring proactive pour une application en production.

1. État des Conteneurs

# 🇬🇧 Check running containers / 🇫🇷 Vérifier les conteneurs actifs
docker ps
# 🇬🇧 Check all containers (including stopped) / 🇫🇷 Voir tous les conteneurs (y compris arrêtés)
docker ps -a
# 🇬🇧 Container resource usage / 🇫🇷 Utilisation des ressources par conteneur
docker stats
# 🇬🇧 Container details / 🇫🇷 Détails d'un conteneur
docker inspect [CONTAINER_NAME]

2. Logs et Debugging

# 🇬🇧 View container logs / 🇫🇷 Voir les logs d'un conteneur
docker logs [CONTAINER_NAME]
# 🇬🇧 Follow logs in real-time / 🇫🇷 Suivre les logs en temps réel
docker logs -f [CONTAINER_NAME]
# 🇬🇧 Last 100 lines of logs / 🇫🇷 100 dernières lignes de logs
docker logs --tail 100 [CONTAINER_NAME]
# 🇬🇧 Logs with timestamps / 🇫🇷 Logs avec horodatage
docker logs -t [CONTAINER_NAME]

3. Accès aux Conteneurs

# 🇬🇧 Access container shell / 🇫🇷 Accéder au shell du conteneur
docker exec -it [CONTAINER_NAME] /bin/bash
# 🇬🇧 For Alpine-based containers / 🇫🇷 Pour les conteneurs basés sur Alpine
docker exec -it [CONTAINER_NAME] /bin/sh
# 🇬🇧 Execute specific command / 🇫🇷 Exécuter une commande spécifique
docker exec [CONTAINER_NAME] [COMMAND]

4. Vérifications Spécifiques monapplication

# 🇬🇧 Check Laravel API health / 🇫🇷 Vérifier la santé de l'API Laravel
docker exec api php artisan route:list
docker exec api php artisan config:cache
# 🇬🇧 Check database connection / 🇫🇷 Vérifier la connexion base de données
docker exec api php artisan migrate:status
# 🇬🇧 Check MySQL database / 🇫🇷 Vérifier la base MySQL
docker exec -it db mysql -u root -p
# 🇬🇧 Frontend build verification / 🇫🇷 Vérification du build frontend
docker exec frontend ls -la /usr/share/nginx/html

 

 

Configuration Docker Compose pour Production

Fichier : deploy/docker-compose.yml

version: '3.8'
services:
 # 🇬🇧 Traefik Reverse Proxy / 🇫🇷 Proxy inverse Traefik
 traefik:
 image: traefik:v3.2
 container_name: traefik
 restart: unless-stopped
 ports:
 - "80:80"
 - "443:443"
 volumes:
 - /var/run/docker.sock:/var/run/docker.sock:ro
 - ./traefik.yml:/etc/traefik/traefik.yml:ro
 - ./acme.json:/acme.json
 networks:
 - monapplication
 # 🇬🇧 MySQL Database / 🇫🇷 Base de données MySQL
 db:
 image: mysql:8.0
 container_name: db
 restart: unless-stopped
 environment:
 MYSQL_ROOT_PASSWORD: ${MYSQL_ROOT_PASSWORD}
 MYSQL_DATABASE: monapplication
 MYSQL_USER: monapplication
 MYSQL_PASSWORD: ${DB_PASSWORD}
 volumes:
 - mysql_data:/var/lib/mysql
 - ./mysql.cnf:/etc/mysql/conf.d/custom.cnf:ro
 networks:
 - monapplication
 healthcheck:
 test: ["CMD", "mysqladmin", "ping", "-h", "localhost"]
 timeout: 20s
 retries: 10
 # 🇬🇧 Laravel API / 🇫🇷 API Laravel
 api:
 image: ghcr.io/nataswim/monapplication-api:${IMAGE_TAG:-latest}
 container_name: api
 restart: unless-stopped
 environment:
 APP_ENV: production
 APP_DEBUG: false
 APP_KEY: ${APP_KEY}
 DB_HOST: db
 DB_DATABASE: monapplication
 DB_USERNAME: monapplication
 DB_PASSWORD: ${DB_PASSWORD}
 JWT_SECRET: ${JWT_SECRET}
 MAIL_PASSWORD: ${MAIL_PASSWORD}
 volumes:
 - api_storage:/var/www/html/storage
 - api_uploads:/var/www/html/public/uploads
 networks:
 - monapplication
 depends_on:
 db:
 condition: service_healthy
 labels:
 - "traefik.enable=true"
 - "traefik.http.routers.api.rule=Host(`monapplication.com`) && PathPrefix(`/api`)"
 - "traefik.http.routers.api.tls=true"
 - "traefik.http.routers.api.tls.certresolver=letsencrypt"
 # 🇬🇧 React Frontend / 🇫🇷 Frontend React
 frontend:
 image: ghcr.io/nataswim/monapplication-spa:${IMAGE_TAG:-latest}
 container_name: frontend
 restart: unless-stopped
 networks:
 - monapplication
 depends_on:
 - api
 labels:
 - "traefik.enable=true"
 - "traefik.http.routers.frontend.rule=Host(`monapplication.com`)"
 - "traefik.http.routers.frontend.tls=true"
 - "traefik.http.routers.frontend.tls.certresolver=letsencrypt"
networks:
 monapplication:
 external: true
volumes:
 mysql_data:
 api_storage:
 api_uploads:

 

Fichier : deploy/.env

# 🇬🇧 Production Environment Variables / 🇫🇷 Variables d'environnement de production
# Image versions
IMAGE_TAG=latest
# Database
MYSQL_ROOT_PASSWORD=your-secure-root-password
DB_PASSWORD=your-secure-db-password
# Laravel
APP_KEY=base64:your-generated-app-key
JWT_SECRET=your-jwt-secret-key
# Mail
MAIL_PASSWORD=your-mail-password
# Domain
DOMAIN=monapplication.com

 

Commandes d’Interaction

Gestion des Conteneurs

# 🇬🇧 Start containers / 🇫🇷 Démarrer les conteneurs
docker-compose up -d
# 🇬🇧 Stop containers / 🇫🇷 Arrêter les conteneurs
docker-compose down
# 🇬🇧 Restart specific container / 🇫🇷 Redémarrer un conteneur spécifique
docker restart [CONTAINER_NAME]
# 🇬🇧 Rebuild and restart / 🇫🇷 Reconstruire et redémarrer
docker-compose up -d --build

 

Mise à Jour de l’Application

# 🇬🇧 Pull latest images / 🇫🇷 Récupérer les dernières images
docker-compose pull
# 🇬🇧 Update and restart / 🇫🇷 Mettre à jour et redémarrer
docker-compose down && docker-compose up -d
# 🇬🇧 Force rebuild from GitHub / 🇫🇷 Forcer la reconstruction depuis GitHub
docker-compose up -d --build --force-recreate

 

Maintenance Laravel

# 🇬🇧 Clear all Laravel caches / 🇫🇷 Vider tous les caches Laravel
docker exec api php artisan cache:clear
docker exec api php artisan config:clear
docker exec api php artisan route:clear
docker exec api php artisan view:clear
# 🇬🇧 Run migrations / 🇫🇷 Exécuter les migrations
docker exec api php artisan migrate
# 🇬🇧 Seed database / 🇫🇷 Alimenter la base de données
docker exec api php artisan db:seed
# 🇬🇧 Generate application key / 🇫🇷 Générer la clé d'application
docker exec api php artisan key:generate

 

 

Commandes de Sauvegarde

==> Objectif : Protéger vos données critiques avec des stratégies de sauvegarde robustes et automatisées pour garantir la continuité de service.

La protection des données est cruciale pour toute application en production. Cette section présente les meilleures pratiques pour sauvegarder votre base de données MySQL, vos fichiers applicatifs et vos volumes Docker, avec des scripts d’automatisation et des stratégies de rétention optimisées.

 

Sauvegarde Base de Données

# 🇬🇧 Create MySQL backup / 🇫🇷 Créer une sauvegarde MySQL
docker exec db mysqldump -u root -p[PASSWORD] monapplication > backup_$(date +%Y%m%d_%H%M%S).sql
# 🇬🇧 Backup with compression / 🇫🇷 Sauvegarde avec compression
docker exec db mysqldump -u root -p[PASSWORD] monapplication | gzip > backup_$(date +%Y%m%d_%H%M%S).sql.gz
# 🇬🇧 Restore database / 🇫🇷 Restaurer la base de données
docker exec -i db mysql -u root -p[PASSWORD] monapplication < backup_file.sql

 

Sauvegarde Volumes et Fichiers

# 🇬🇧 Backup application files / 🇫🇷 Sauvegarder les fichiers d'application
tar -czf monapplication_backup_$(date +%Y%m%d).tar.gz /path/to/monapplication/
# 🇬🇧 Backup Docker volumes / 🇫🇷 Sauvegarder les volumes Docker
docker run --rm -v [VOLUME_NAME]:/data -v $(pwd):/backup alpine tar czf /backup/volume_backup.tar.gz /data
# 🇬🇧 Create full system backup / 🇫🇷 Créer une sauvegarde système complète
rsync -avz --exclude='node_modules' /path/to/monapplication/ /backup/location/

 

Sauvegarde Automatisée

# 🇬🇧 Create backup script / 🇫🇷 Créer un script de sauvegarde
cat > backup_monapplication.sh << 'EOF'
#!/bin/bash
DATE=$(date +%Y%m%d_%H%M%S)
BACKUP_DIR="/backup/monapplication"
mkdir -p $BACKUP_DIR
# Database backup
docker exec db mysqldump -u root -p$MYSQL_ROOT_PASSWORD monapplication | gzip > $BACKUP_DIR/db_$DATE.sql.gz
# Files backup
tar -czf $BACKUP_DIR/files_$DATE.tar.gz /path/to/monapplication/
# Keep only last 7 days
find $BACKUP_DIR -name "*.gz" -mtime +7 -delete
echo "Backup completed: $DATE"
EOF
chmod +x backup_monapplication.sh
# 🇬🇧 Add to crontab (daily at 2 AM) / 🇫🇷 Ajouter au crontab (quotidien à 2h)
echo "0 2 * * * /root/backup_monapplication.sh" | crontab -

 

 

Troubleshooting

 Objectif : Résoudre rapidement les incidents et restaurer le service avec des procédures de diagnostic et de récupération éprouvées.

Quand les problèmes surviennent, chaque minute compte. Cette section vous équipe avec les outils de diagnostic essentiels et les procédures d’urgence pour identifier, analyser et résoudre efficacement les pannes, minimisant ainsi l’impact sur vos utilisateurs.

Problèmes Courants

# 🇬🇧 Check container health / 🇫🇷 Vérifier la santé des conteneurs
docker ps --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}"
# 🇬🇧 Check disk space / 🇫🇷 Vérifier l'espace disque
df -h
docker system df
# 🇬🇧 Clean unused Docker resources / 🇫🇷 Nettoyer les ressources Docker inutilisées
docker system prune -a
# 🇬🇧 Check memory usage / 🇫🇷 Vérifier l'utilisation mémoire
free -h
docker stats --no-stream

 

Redémarrage d’Urgence

# 🇬🇧 Emergency restart all services / 🇫🇷 Redémarrage d'urgence de tous les services
docker-compose down && docker-compose up -d
# 🇬🇧 Force stop and remove all containers / 🇫🇷 Arrêt forcé et suppression des conteneurs
docker stop $(docker ps -q) && docker rm $(docker ps -aq)
# 🇬🇧 Restart Docker daemon / 🇫🇷 Redémarrer le démon Docker
sudo systemctl restart docker

 

Logs de Debug

# 🇬🇧 Check all container logs / 🇫🇷 Vérifier tous les logs des conteneurs
for container in $(docker ps --format "{{.Names}}"); do
 echo "=== $container ==="
 docker logs --tail 20 $container
done
# 🇬🇧 Check system logs / 🇫🇷 Vérifier les logs système
journalctl -u docker -f

 

Monitoring et Performance

==> Objectif : Optimiser les performances de votre application et anticiper les problèmes grâce à une surveillance proactive et des métriques pertinentes.

Une surveillance efficace est la clé d’une application performante et stable. Cette section vous guide dans la mise en place d’un monitoring complet, de l’analyse des ressources système à l’optimisation des performances, pour maintenir une expérience utilisateur optimale.

Surveillance en Temps Réel

# 🇬🇧 Monitor all containers / 🇫🇷 Surveiller tous les conteneurs
watch -n 2 'docker stats --no-stream'
# 🇬🇧 Network monitoring / 🇫🇷 Surveillance réseau
docker network ls
docker network inspect [NETWORK_NAME]
# 🇬🇧 Port monitoring / 🇫🇷 Surveillance des ports
netstat -tulpn | grep LISTEN

 

Optimisation

# 🇬🇧 Remove unused images / 🇫🇷 Supprimer les images inutilisées
docker image prune -a
# 🇬🇧 Remove unused volumes / 🇫🇷 Supprimer les volumes inutilisés
docker volume prune
# 🇬🇧 Clean everything / 🇫🇷 Nettoyer tout
docker system prune -a --volumes

 

Sécurité

==> Objectif : Sécuriser votre infrastructure et protéger vos données contre les menaces avec des pratiques de sécurité éprouvées et des contrôles d’accès stricts.

La sécurité de votre application ne doit jamais être négligée. Cette section couvre les aspects essentiels de la sécurisation d’une infrastructure Docker en production, de la gestion des mises à jour de sécurité à la surveillance des accès, pour maintenir un niveau de protection optimal.

Vérifications de Sécurité

# 🇬🇧 Check for security updates / 🇫🇷 Vérifier les mises à jour de sécurité
sudo apt update && sudo apt list --upgradable
# 🇬🇧 Update Docker images / 🇫🇷 Mettre à jour les images Docker
docker-compose pull && docker-compose up -d
# 🇬🇧 Check exposed ports / 🇫🇷 Vérifier les ports exposés
nmap localhost

Surveillance des Accès

# 🇬🇧 Check nginx access logs / 🇫🇷 Vérifier les logs d'accès nginx
docker logs frontend | grep -E "GET|POST|PUT|DELETE"
# 🇬🇧 Monitor failed login attempts / 🇫🇷 Surveiller les tentatives de connexion échouées
grep "Failed" /var/log/auth.log

 

 

Lexique

==> Objectif : Maîtriser la terminologie technique pour une communication efficace et une compréhension approfondie des technologies utilisées.

Ce glossaire technique définit les termes essentiels utilisés dans ce guide. Il constitue une référence rapide pour comprendre les concepts Docker, VPS et Laravel, facilitant ainsi l’assimilation des procédures et la communication technique au sein de votre équipe.

Termes Docker

  • Container : Instance d’exécution d’une image Docker
  • Image : Template read-only pour créer des containers
  • Volume : Système de stockage persistant Docker
  • Network : Réseau virtuel Docker pour la communication inter-conteneurs
  • Compose : Outil pour définir et exécuter des applications multi-conteneurs
  • Registry : Service de stockage et distribution d’images Docker

Termes VPS

  • VPS : Virtual Private Server (Serveur Privé Virtuel)
  • SSH : Secure Shell, protocole de connexion sécurisée
  • Reverse Proxy : Serveur intermédiaire qui distribue les requêtes
  • Load Balancer : Répartiteur de charge
  • SSL/TLS : Protocoles de sécurisation des communications

Termes Laravel

  • Artisan : Interface en ligne de commande de Laravel
  • Migration : Script de modification de base de données
  • Seeder : Script d’insertion de données de test
  • Cache : Système de mise en cache des données
  • Middleware : Couche intermédiaire de traitement des requêtes

 

Liens Utiles

==> Objectif : Accéder rapidement aux ressources officielles et outils complémentaires pour approfondir vos connaissances et résoudre des problèmes spécifiques.

Cette bibliothèque de ressources rassemble les documentations officielles, guides de bonnes pratiques et outils recommandés pour compléter ce guide. Ces liens constituent votre base de référence pour rester à jour avec les évolutions technologiques et les meilleures pratiques du secteur.

Documentation Docker

Gestion VPS

Laravel & React

Monitoring & Maintenance

GitHub Actions & CI/CD

Outils Recommandés

  • Portainer : Interface graphique pour Docker
  • Watchtower : Mise à jour automatique des conteneurs
  • Traefik : Reverse proxy et load balancer moderne
  • Let’s Encrypt : Certificats SSL gratuits
  • Act : Tester GitHub Actions localement

 

Déploiement et GitHub Actions

==> Objectif : Automatiser vos déploiements avec un pipeline CI/CD robuste et des stratégies de mise en production zero-downtime pour une livraison continue et fiable.

Le déploiement automatisé est essentiel pour maintenir un rythme de développement soutenu tout en garantissant la stabilité. Cette section détaille la mise en place d’un pipeline CI/CD complet avec GitHub Actions, des stratégies de déploiement avancées et la gestion des versions pour une livraison continue professionnelle.

 

Commandes de Déploiement Local

# 🇬🇧 Deploy from GitHub Registry / 🇫🇷 Déployer depuis GitHub Registry
cd /path/to/monapplication
docker-compose pull
docker-compose up -d
# 🇬🇧 Force pull latest images / 🇫🇷 Forcer le téléchargement des dernières images
docker pull ghcr.io/nataswim/monapplication-spa:latest
docker pull ghcr.io/nataswim/monapplication-api:latest
# 🇬🇧 Deploy specific commit / 🇫🇷 Déployer un commit spécifique
docker pull ghcr.io/nataswim/monapplication-spa:661bf95820f16a8cca7cdd720711e41a1f5ebe37
docker pull ghcr.io/nataswim/monapplication-api:661bf95820f16a8cca7cdd720711e41a1f5ebe37
docker-compose up -d

 

GitHub Registry (GHCR) Management

# 🇬🇧 Login to GitHub Registry / 🇫🇷 Se connecter au registre GitHub
echo $GITHUB_TOKEN | docker login ghcr.io -u USERNAME --password-stdin
# 🇬🇧 List available images / 🇫🇷 Lister les images disponibles
curl -H "Authorization: Bearer $GITHUB_TOKEN" \
 https://ghcr.io/v2/nataswim/monapplication-spa/tags/list
# 🇬🇧 Pull specific tag / 🇫🇷 Télécharger un tag spécifique
docker pull ghcr.io/nataswim/monapplication-spa:develop
docker pull ghcr.io/nataswim/monapplication-api:develop
# 🇬🇧 Tag and push local image / 🇫🇷 Tagger et pousser une image locale
docker tag local-image ghcr.io/nataswim/monapplication-spa:custom-tag
docker push ghcr.io/nataswim/monapplication-spa:custom-tag

 

Workflow GitHub Actions

Fichier : .github/workflows/deploy.yml

name: 🚀 Deploy monapplication
# 🇬🇧 Triggered on push to main branch / 🇫🇷 Déclenché lors du push sur main
on:
 push:
 branches: [ main, develop ]
 pull_request:
 branches: [ main ]
env:
 REGISTRY: ghcr.io
 IMAGE_NAME_API: ${{ github.repository }}-api
 IMAGE_NAME_SPA: ${{ github.repository }}-spa
jobs:
 # 🇬🇧 Build and push Docker images / 🇫🇷 Construire et pousser les images Docker
 build:
 runs-on: ubuntu-latest
 permissions:
 contents: read
 packages: write
 steps:
 - name: 📥 Checkout repository
 uses: actions/checkout@v4
 - name: 🔐 Log in to Container Registry
 uses: docker/login-action@v3
 with:
 registry: ${{ env.REGISTRY }}
 username: ${{ github.actor }}
 password: ${{ secrets.GITHUB_TOKEN }}
 - name: 📋 Extract metadata (API)
 id: meta-api
 uses: docker/metadata-action@v5
 with:
 images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME_API }}
 tags: |
 type=ref,event=branch
 type=ref,event=pr
 type=sha,prefix={{branch}}-
 type=raw,value=latest,enable={{is_default_branch}}
 - name: 📋 Extract metadata (SPA)
 id: meta-spa
 uses: docker/metadata-action@v5
 with:
 images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME_SPA }}
 tags: |
 type=ref,event=branch
 type=ref,event=pr
 type=sha,prefix={{branch}}-
 type=raw,value=latest,enable={{is_default_branch}}
 - name: 🏗️ Build and push API image
 uses: docker/build-push-action@v5
 with:
 context: ./back
 file: ./back/Dockerfile
 push: true
 tags: ${{ steps.meta-api.outputs.tags }}
 labels: ${{ steps.meta-api.outputs.labels }}
 - name: 🏗️ Build and push SPA image
 uses: docker/build-push-action@v5
 with:
 context: ./front
 file: ./front/Dockerfile
 push: true
 tags: ${{ steps.meta-spa.outputs.tags }}
 labels: ${{ steps.meta-spa.outputs.labels }}
 # 🇬🇧 Deploy to VPS / 🇫🇷 Déployer sur le VPS
 deploy:
 needs: build
 runs-on: ubuntu-latest
 if: github.ref == 'refs/heads/main'
 steps:
 - name: 🚀 Deploy to VPS
 uses: appleboy/ssh-action@v1.0.0
 with:
 host: ${{ secrets.VPS_HOST }}
 username: ${{ secrets.VPS_USER }}
 key: ${{ secrets.VPS_SSH_KEY }}
 port: ${{ secrets.VPS_PORT }}
 script: |
 cd /path/to/monapplication
 echo "🔄 Pulling latest images..."
 docker-compose pull
 echo "🚀 Restarting services..."
 docker-compose up -d
 echo "🧹 Cleaning up..."
 docker image prune -f
 echo "✅ Deployment completed!"

 

Fichier : .github/workflows/tests.yml

name: 🧪 Tests monapplication
on:
 push:
 branches: [ main, develop ]
 pull_request:
 branches: [ main ]
jobs:
 # 🇬🇧 Laravel API Tests / 🇫🇷 Tests API Laravel
 laravel-tests:
 runs-on: ubuntu-latest
 services:
 mysql:
 image: mysql:8.0
 env:
 MYSQL_ROOT_PASSWORD: password
 MYSQL_DATABASE: monapplication_test
 options: >-
 --health-cmd="mysqladmin ping"
 --health-interval=10s
 --health-timeout=5s
 --health-retries=3
 steps:
 - name: 📥 Checkout code
 uses: actions/checkout@v4
 - name: 🐘 Setup PHP
 uses: shivammathur/setup-php@v2
 with:
 php-version: '8.2'
 extensions: mbstring, dom, fileinfo, mysql
 - name: 📦 Install dependencies
 working-directory: ./back
 run: |
 composer install --no-interaction --prefer-dist --optimize-autoloader
 - name: 🔧 Setup environment
 working-directory: ./back
 run: |
 cp .env.example .env.testing
 php artisan key:generate --env=testing
 - name: 🗄️ Run migrations
 working-directory: ./back
 run: php artisan migrate --env=testing
 - name: 🧪 Run tests
 working-directory: ./back
 run: php artisan test
 # 🇬🇧 React Frontend Tests / 🇫🇷 Tests Frontend React
 react-tests:
 runs-on: ubuntu-latest
 steps:
 - name: 📥 Checkout code
 uses: actions/checkout@v4
 - name: 📦 Setup Node.js
 uses: actions/setup-node@v4
 with:
 node-version: '20'
 cache: 'npm'
 cache-dependency-path: ./front/package-lock.json
 - name: 📦 Install dependencies
 working-directory: ./front
 run: npm ci
 - name: 🏗️ Build application
 working-directory: ./front
 run: npm run build
 - name: 🧪 Run tests
 working-directory: ./front
 run: npm test -- --coverage --watchAll=false

 

Scripts de Déploiement Automatisé

Script : deploy/deploy.sh

#!/bin/bash
# 🇬🇧 monapplication Deployment Script / 🇫🇷 Script de déploiement monapplication
# Usage: ./deploy.sh [environment] [branch]
set -e # Exit on any error
ENVIRONMENT=${1:-production}
BRANCH=${2:-main}
TIMESTAMP=$(date +%Y%m%d_%H%M%S)
echo "🚀 Starting deployment of monapplication"
echo "📅 Timestamp: $TIMESTAMP"
echo "🌍 Environment: $ENVIRONMENT"
echo "🌿 Branch: $BRANCH"
# 🇬🇧 Pre-deployment checks / 🇫🇷 Vérifications pré-déploiement
echo "🔍 Pre-deployment checks..."
docker --version || { echo "❌ Docker not installed"; exit 1; }
docker-compose --version || { echo "❌ Docker Compose not installed"; exit 1; }
# 🇬🇧 Backup current state / 🇫🇷 Sauvegarde de l'état actuel
echo "💾 Creating backup..."
mkdir -p /backup/monapplication/$TIMESTAMP
docker exec db mysqldump -u root -p$MYSQL_ROOT_PASSWORD monapplication | gzip > /backup/monapplication/$TIMESTAMP/db_backup.sql.gz
# 🇬🇧 Pull latest images / 🇫🇷 Télécharger les dernières images
echo "📥 Pulling latest images..."
docker-compose pull
# 🇬🇧 Deploy with zero downtime / 🇫🇷 Déploiement sans interruption
echo "🔄 Updating services..."
docker-compose up -d --remove-orphans
# 🇬🇧 Wait for services to be ready / 🇫🇷 Attendre que les services soient prêts
echo "⏳ Waiting for services..."
sleep 30
# 🇬🇧 Run Laravel maintenance / 🇫🇷 Maintenance Laravel
echo "🔧 Running Laravel maintenance..."
docker exec api php artisan migrate --force
docker exec api php artisan config:cache
docker exec api php artisan route:cache
docker exec api php artisan view:cache
# 🇬🇧 Health checks / 🇫🇷 Vérifications de santé
echo "🏥 Running health checks..."
FRONTEND_STATUS=$(curl -s -o /dev/null -w "%{http_code}" https://monapplication.com || echo "000")
API_STATUS=$(curl -s -o /dev/null -w "%{http_code}" https://monapplication.com/api/health || echo "000")
if [ "$FRONTEND_STATUS" = "200" ] && [ "$API_STATUS" = "200" ]; then
 echo "✅ Health checks passed"
 echo "🌐 Frontend: $FRONTEND_STATUS"
 echo "🔌 API: $API_STATUS"
else
 echo "❌ Health checks failed"
 echo "🌐 Frontend: $FRONTEND_STATUS"
 echo "🔌 API: $API_STATUS"
 echo "🔄 Rolling back..."
 # Add rollback logic here
 exit 1
fi
# 🇬🇧 Cleanup / 🇫🇷 Nettoyage
echo "🧹 Cleaning up..."
docker image prune -f
docker system prune -f --volumes=false
echo "✅ Deployment completed successfully!"
echo "📊 Deployment summary:"
docker ps --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}"

 

Script : deploy/rollback.sh

#!/bin/bash
# 🇬🇧 monapplication Rollback Script / 🇫🇷 Script de retour en arrière monapplication
# Usage: ./rollback.sh [backup_timestamp]
BACKUP_TIMESTAMP=${1}
if [ -z "$BACKUP_TIMESTAMP" ]; then
 echo "❌ Please provide backup timestamp"
 echo "Available backups:"
 ls -la /backup/monapplication/
 exit 1
fi
echo "🔄 Rolling back to: $BACKUP_TIMESTAMP"
# 🇬🇧 Stop current services / 🇫🇷 Arrêter les services actuels
docker-compose down
# 🇬🇧 Restore database / 🇫🇷 Restaurer la base de données
echo "🗄️ Restoring database..."
zcat /backup/monapplication/$BACKUP_TIMESTAMP/db_backup.sql.gz | docker exec -i db mysql -u root -p$MYSQL_ROOT_PASSWORD monapplication
# 🇬🇧 Start services / 🇫🇷 Démarrer les services
docker-compose up -d
echo "✅ Rollback completed!"

 

GitHub Secrets Configuration

Secrets Requis dans GitHub

# 🇬🇧 VPS Connection / 🇫🇷 Connexion VPS
VPS_HOST=your-vps-ip-or-domain
VPS_USER=root
VPS_SSH_KEY=your-private-ssh-key
VPS_PORT=22
# 🇬🇧 Database / 🇫🇷 Base de données
DB_PASSWORD=your-secure-password
MYSQL_ROOT_PASSWORD=your-mysql-root-password
# 🇬🇧 Laravel / 🇫🇷 Laravel
APP_KEY=base64:your-laravel-app-key
JWT_SECRET=your-jwt-secret
# 🇬🇧 External Services / 🇫🇷 Services externes
MAIL_PASSWORD=your-mail-password

 

Commandes pour Gérer les Secrets

# 🇬🇧 Generate SSH key for deployment / 🇫🇷 Générer une clé SSH pour le déploiement
ssh-keygen -t rsa -b 4096 -C "github-actions@monapplication.com" -f deploy_key
# 🇬🇧 Add public key to VPS / 🇫🇷 Ajouter la clé publique au VPS
cat deploy_key.pub >> ~/.ssh/authorized_keys
# 🇬🇧 Add private key to GitHub Secrets / 🇫🇷 Ajouter la clé privée aux secrets GitHub
# Copy content of deploy_key to VPS_SSH_KEY secret
# 🇬🇧 Generate Laravel APP_KEY / 🇫🇷 Générer la clé APP_KEY Laravel
docker exec api php artisan key:generate --show

 

Commandes de Monitoring des Déploiements

# 🇬🇧 Monitor deployment logs / 🇫🇷 Surveiller les logs de déploiement
tail -f /var/log/deployment.log
# 🇬🇧 Check GitHub Actions status / 🇫🇷 Vérifier le statut GitHub Actions
curl -H "Authorization: token $GITHUB_TOKEN" \
 https://api.github.com/repos/nataswim/monapplication/actions/runs
# 🇬🇧 Verify image tags / 🇫🇷 Vérifier les tags d'images
docker images | grep ghcr.io/nataswim/monapplication
# 🇬🇧 Check deployment history / 🇫🇷 Vérifier l'historique des déploiements
docker exec api php artisan migrate:status
docker exec api php artisan --version

 

Stratégies de Déploiement

Rolling Update (Recommandé)

# 🇬🇧 Update services one by one / 🇫🇷 Mettre à jour les services un par un
docker-compose up -d --no-deps frontend
sleep 10
docker-compose up -d --no-deps api
sleep 10
docker-compose up -d --no-deps db

Blue-Green Deployment

# 🇬🇧 Create green environment / 🇫🇷 Créer l'environnement vert
docker-compose -f docker-compose.green.yml up -d
# 🇬🇧 Test green environment / 🇫🇷 Tester l'environnement vert
curl -f http://green.monapplication.com/health
# 🇬🇧 Switch traffic to green / 🇫🇷 Basculer le trafic vers le vert
# Update load balancer configuration
# 🇬🇧 Stop blue environment / 🇫🇷 Arrêter l'environnement bleu
docker-compose -f docker-compose.blue.yml down

 

Tests et Debug GitHub Actions

# 🇬🇧 Install Act (test GitHub Actions locally) / 🇫🇷 Installer Act (tester GitHub Actions localement)
curl https://raw.githubusercontent.com/nektos/act/master/install.sh | sudo bash
# 🇬🇧 Test workflow locally / 🇫🇷 Tester le workflow localement
act -n # Dry run
act push # Test on push event
act pull_request # Test on PR event
# 🇬🇧 Test specific job / 🇫🇷 Tester un job spécifique
act -j build
act -j deploy
# 🇬🇧 Debug with secrets / 🇫🇷 Déboguer avec les secrets
act --secret-file .secrets push
# 🇬🇧 Verbose output / 🇫🇷 Sortie détaillée
act -v push
# 🇬🇧 Check workflow syntax / 🇫🇷 Vérifier la syntaxe du workflow
yamllint .github/workflows/*.yml

 

Commandes de Déploiement Avancées

# 🇬🇧 Deploy specific version / 🇫🇷 Déployer une version spécifique
export IMAGE_TAG="v1.2.3"
docker-compose -f docker-compose.prod.yml up -d
# 🇬🇧 Canary deployment (10% traffic) / 🇫🇷 Déploiement canari (10% du trafic)
docker run -d --name frontend-canary \
 -l "traefik.http.services.frontend-canary.loadbalancer.weight=10" \
 ghcr.io/nataswim/monapplication-spa:canary
# 🇬🇧 Feature flag deployment / 🇫🇷 Déploiement avec feature flags
docker run -d --name api-feature \
 -e FEATURE_NEW_API=true \
 ghcr.io/nataswim/monapplication-api:feature-branch
# 🇬🇧 Multi-environment deployment / 🇫🇷 Déploiement multi-environnements
for env in staging production; do
 docker-compose -f docker-compose.$env.yml up -d
done
# 🇬🇧 Automated testing after deployment / 🇫🇷 Tests automatisés après déploiement
curl -f https://monapplication.com/health || \
 (echo "❌ Health check failed, rolling back..." && ./rollback.sh)

 

Notifications de Déploiement

# 🇬🇧 Slack notification script / 🇫🇷 Script de notification Slack
send_slack_notification() {
 curl -X POST -H 'Content-type: application/json' \
 --data "{\"text\":\"🚀 monapplication deployed successfully to production!\"}" \
 $SLACK_WEBHOOK_URL
}
# 🇬🇧 Discord notification / 🇫🇷 Notification Discord
send_discord_notification() {
 curl -X POST -H 'Content-Type: application/json' \
 --data "{\"content\":\"✅ Deployment completed: $(date)\"}" \
 $DISCORD_WEBHOOK_URL
}
# 🇬🇧 Email notification / 🇫🇷 Notification par email
send_email_notification() {
 echo "Deployment completed at $(date)" | \
 mail -s "monapplication Deployment Success" admin@monapplication.com
}

 

Scripts Utiles

Script de Surveillance (monitor.sh)

#!/bin/bash
echo "=== monapplication Status Check ==="
echo "Date: $(date)"
echo ""
echo "=== Docker Containers ==="
docker ps --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}"
echo ""
echo "=== System Resources ==="
echo "Memory: $(free -h | grep Mem | awk '{print $3"/"$2}')"
echo "Disk: $(df -h / | tail -1 | awk '{print $3"/"$2" ("$5" used)"}')"
echo ""
echo "=== Application Health ==="
curl -s -o /dev/null -w "Frontend: %{http_code}\n" https://monapplication.com
curl -s -o /dev/null -w "API: %{http_code}\n" https://monapplication.com/api/health

 

Gestion des Versions et Tags

# 🇬🇧 List all available tags / 🇫🇷 Lister tous les tags disponibles
curl -s "https://ghcr.io/v2/nataswim/monapplication-spa/tags/list" | jq -r '.tags[]'
# 🇬🇧 Deploy specific version / 🇫🇷 Déployer une version spécifique
export IMAGE_TAG="v2.1.0"
docker-compose up -d
# 🇬🇧 Create release tag / 🇫🇷 Créer un tag de release
git tag -a v2.1.0 -m "Release version 2.1.0"
git push origin v2.1.0
# 🇬🇧 Compare deployed version with latest / 🇫🇷 Comparer la version déployée avec la dernière
CURRENT_SHA=$(docker inspect api --format='{{index .Config.Labels "org.opencontainers.image.revision"}}')
LATEST_SHA=$(git rev-parse HEAD)
echo "Current: $CURRENT_SHA"
echo "Latest: $LATEST_SHA"
# 🇬🇧 Deployment with version pinning / 🇫🇷 Déploiement avec épinglage de version
docker-compose -f docker-compose.yml -f docker-compose.prod.yml up -d

 

Commandes de Surveillance Continue

# 🇬🇧 Real-time deployment monitoring / 🇫🇷 Surveillance en temps réel des déploiements
watch -n 5 'echo "=== Container Status ===" && docker ps --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}" && echo "" && echo "=== Health Checks ===" && curl -s https://monapplication.com/health | jq .'
# 🇬🇧 Log aggregation for debugging / 🇫🇷 Agrégation de logs pour le débogage
docker-compose logs -f --tail=100 | grep -E "(ERROR|WARNING|CRITICAL)"
# 🇬🇧 Performance monitoring / 🇫🇷 Surveillance des performances
docker stats --format "table {{.Container}}\t{{.CPUPerc}}\t{{.MemUsage}}\t{{.NetIO}}" --no-stream
# 🇬🇧 Automated health check with notifications / 🇫🇷 Vérification automatique avec notifications
#!/bin/bash
health_check() {
 STATUS=$(curl -s -o /dev/null -w "%{http_code}" https://monapplication.com/health)
 if [ "$STATUS" != "200" ]; then
 echo "🚨 ALERT: monapplication health check failed (Status: $STATUS)"
 # Send notification here
 ./send_alert.sh "Health check failed"
 else
 echo "✅ monapplication is healthy (Status: $STATUS)"
 fi
}

 

Scripts de Déploiement Rapide (deploy.sh)

#!/bin/bash
echo "🚀 Deploying monapplication..."
cd /path/to/monapplication
git pull origin main
docker-compose pull
docker-compose up -d
docker exec api php artisan migrate --force
docker exec api php artisan config:cache
echo "✅ Deployment completed!"