From 153a7d480734bd2bab6f427bfd271b47b0f7ef15 Mon Sep 17 00:00:00 2001 From: Andrey Date: Sun, 25 Jan 2026 15:44:21 +0300 Subject: [PATCH] chore: refine CI and deployment workflows with enhanced notifications and checks - Improved CI workflow notifications for better clarity on test results. - Added a status check job in the deployment workflow to ensure only successful builds are deployed. - Updated deployment notification messages for improved context and clarity. --- .github/workflows/pipeline.yml | 182 +++++++++++++++++++++++++++++++++ 1 file changed, 182 insertions(+) create mode 100644 .github/workflows/pipeline.yml diff --git a/.github/workflows/pipeline.yml b/.github/workflows/pipeline.yml new file mode 100644 index 0000000..32c1387 --- /dev/null +++ b/.github/workflows/pipeline.yml @@ -0,0 +1,182 @@ +name: CI/CD Pipeline + +on: + push: + branches: [ main, develop, 'feature/**' ] + pull_request: + branches: [ main, develop ] + +jobs: + test: + runs-on: ubuntu-latest + name: Test + outputs: + status: ${{ job.status }} + + steps: + - name: Checkout code + uses: actions/checkout@v4 + + - name: Set up Python 3.11 + uses: actions/setup-python@v5 + with: + python-version: '3.11' + cache: 'pip' + + - name: Install dependencies + run: | + python -m pip install --upgrade pip + pip install -r tests/infra/requirements-test.txt + + - name: Run infrastructure tests + run: | + python -m pytest tests/infra/ -v --tb=short + + - name: Validate Prometheus config + run: | + python -m pytest tests/infra/test_prometheus_config.py -v + + - name: Upload test results + if: always() + uses: actions/upload-artifact@v4 + with: + name: test-results + path: | + .pytest_cache/ + htmlcov/ + retention-days: 7 + + - name: Send test results notification + if: always() + uses: appleboy/telegram-action@v1.0.0 + with: + to: ${{ secrets.TELEGRAM_CHAT_ID }} + token: ${{ secrets.TELEGRAM_BOT_TOKEN }} + message: | + 🧪 CI Tests ${{ job.status }} + + Repository: prod + Branch: ${{ github.ref_name }} + Commit: ${{ github.sha }} + Author: ${{ github.actor }} + + ${{ job.status == 'success' && '✅ All tests passed! Ready for deployment.' || '❌ Tests failed! Deployment blocked.' }} + + View details: ${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }} + continue-on-error: true + + deploy: + runs-on: ubuntu-latest + name: Deploy + needs: test + if: needs.test.outputs.status == 'success' && (github.ref == 'refs/heads/main' || github.event_name == 'pull_request') + environment: + name: production + url: https://${{ vars.SERVER_HOST || secrets.SERVER_HOST }} + + steps: + - name: Checkout code + uses: actions/checkout@v4 + + - name: Deploy to server + uses: appleboy/ssh-action@v1.0.0 + with: + host: ${{ vars.SERVER_HOST || secrets.SERVER_HOST }} + username: ${{ vars.SERVER_USER || secrets.SERVER_USER }} + key: ${{ secrets.SSH_PRIVATE_KEY }} + port: ${{ vars.SSH_PORT || secrets.SSH_PORT || 22 }} + script: | + set -e + echo "🚀 Starting deployment..." + + # Переходим в директорию проекта + cd /home/prod + + # Сохраняем текущий коммит для отката + CURRENT_COMMIT=$(git rev-parse HEAD) + echo "Current commit: $CURRENT_COMMIT" > /tmp/last_deploy_commit.txt + + # Обновляем код + echo "📥 Pulling latest changes..." + + # Исправляем права на файлы перед обновлением + sudo chown -R deploy:deploy /home/prod || true + + git fetch origin main + git reset --hard origin/main + + # Устанавливаем правильные права после обновления + sudo chown -R deploy:deploy /home/prod || true + + # Проверяем, что изменения есть + NEW_COMMIT=$(git rev-parse HEAD) + if [ "$CURRENT_COMMIT" = "$NEW_COMMIT" ]; then + echo "ℹ️ No new changes to deploy" + else + echo "✅ Code updated: $CURRENT_COMMIT → $NEW_COMMIT" + fi + + # Перезапускаем сервисы + echo "🔄 Restarting services..." + if command -v make &> /dev/null; then + make restart || docker-compose restart + else + cd /home/prod + docker-compose down + docker-compose up -d --build + fi + + echo "✅ Deployment completed" + + - name: Health check + uses: appleboy/ssh-action@v1.0.0 + with: + host: ${{ vars.SERVER_HOST || secrets.SERVER_HOST }} + username: ${{ vars.SERVER_USER || secrets.SERVER_USER }} + key: ${{ secrets.SSH_PRIVATE_KEY }} + port: ${{ vars.SSH_PORT || secrets.SSH_PORT || 22 }} + script: | + echo "🏥 Running health checks..." + sleep 15 # Даем время сервисам запуститься + + # Проверяем Prometheus + if curl -f http://localhost:9090/-/healthy > /dev/null 2>&1; then + echo "✅ Prometheus is healthy" + else + echo "❌ Prometheus health check failed" + exit 1 + fi + + # Проверяем Grafana + if curl -f http://localhost:3000/api/health > /dev/null 2>&1; then + echo "✅ Grafana is healthy" + else + echo "❌ Grafana health check failed" + exit 1 + fi + + # Проверяем статус контейнеров + echo "📊 Container status:" + cd /home/prod + docker-compose ps || docker ps --filter "name=bots_" + + echo "✅ All health checks passed" + + - name: Send deployment notification + if: always() + uses: appleboy/telegram-action@v1.0.0 + with: + to: ${{ secrets.TELEGRAM_CHAT_ID }} + token: ${{ secrets.TELEGRAM_BOT_TOKEN }} + message: | + 🚀 Deployment ${{ job.status }} + + Repository: prod + Branch: ${{ github.ref_name }} + Commit: ${{ github.sha }} + Author: ${{ github.actor }} + + ${{ job.status == 'success' && '✅ Deployment successful!' || '❌ Deployment failed!' }} + + View details: ${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }} + continue-on-error: true