Вирішення проблем робочого процесу CI/CD за допомогою GitHub Actions для деплою API на VPS

pic

З Новим Роком! 🎉 Вступаючи в новий рік, наповнений можливостями та викликами, саме час вдосконалити наші процеси та впроваджувати автоматизацію в робочі процеси. Сьогодні я хочу поділитися тим, як я вирішував деякі проблеми у своєму робочому процесі GitHub Actions CI/CD під час деплою .NET Web API на віддалений сервер (в моєму випадку, Droplet на Digitalocean).

Цей досвід не тільки оптимізував мій робочий процес, а й став нагадуванням про важливість безпечної обробки чутливих даних — таких як SSH-дані для доступу — за допомогою GitHub Secrets, як ви побачите в прикладах цього матеріалу.

Сценарій

Мій робочий процес GitHub Actions складався з двох основних задач:

  1. Задача на побудову: для публікації артефактів .NET Web API.
  2. Задача на деплой: для перенесення артефактів на віддалений сервер і перезапуску сервісу застосунку.

Проблема

Я зіткнувся з двома основними проблемами:

  1. Крок завантаження артефактів у задачі побудови вказував на неправильну директорію публікації.
  2. Крок деплою не вдалося виконати через відсутність опублікованих файлів і неправильну обробку віддалених директорій.

Рішення

Ось як я вирішив ці проблеми:

1. Налаштування GitHub Secrets для чутливих даних

Перш за все, я переконався, що вся чутлива інформація, така як SSH-дані, зберігається в GitHub Secrets. Така практика допомагає захистити дані з високим рівнем чутливості, зокрема:

  • SSH_HOST
  • SSH_USER
  • SSH_KEY
  • SSH_PASSPHRASE

Ці секрети використовувались у робочому процесі безпечно, гарантуючи, що вони не потраплять в логи.

2. Правильне визначення директорії публікації

Задача побудови використовувала наступний крок для того, щоб артефакти публікувались у правильну директорію:

- name: Publish API  
 id: publish_api  
 run: |  
 API_PROJECT_PATH="CompanyName.ProductName.API"  
 PUBLISH_DIR="$(pwd)/$API_PROJECT_PATH/publish" # Явно задаємо шлях публікації  
 dotnet publish $API_PROJECT_PATH/CompanyName.ProductName.API.csproj -c Release --no-build --no-restore --property:PublishDir=$PUBLISH_DIR  
 echo "publish_path=$PUBLISH_DIR" >> $GITHUB_ENV

3. Перенесення файлів на віддалений сервер

Задача деплою використовує appleboy/scp-action для безпечного перенесення артефактів на віддалений сервер:

- name: Transfer Files to Remote Server  
 uses: appleboy/[email protected]  
 with:  
 source: ./publish/*  
 target: /my/full/application/path/  
 host: ${{ secrets.SSH_HOST }}  
 username: ${{ secrets.SSH_USER }}  
 key: ${{ secrets.SSH_KEY }}  
 passphrase: ${{ secrets.SSH_PASSPHRASE }}  
 overwrite: true

Це гарантувало, що:

  • Цільова директорія створюється, якщо вона не існує.
  • Файли передаються безпечно.
  • Існуючі файли в цільовій директорії перезаписуються за потреби.

4. Перезапуск застосунку

Останнім кроком було перезапуск сервісу застосунку, налаштованого як Linux Daemon (systemd).
The step uses appleboy/ssh-action to remotely access the server and run commands to restart the service:

- name: Restart Web API Service  
 uses: appleboy/[email protected]  
 with:  
 host: ${{ secrets.SSH_HOST }}  
 key: ${{ secrets.SSH_KEY }}  
 username: ${{ secrets.SSH_USER }}  
 passphrase: ${{ secrets.SSH_PASSPHRASE }}  
 script: |  
 sudo chown -R www-data:www-data /my/full/application/path/  
 sudo systemctl restart apiservice

Повний скрипт робочого процесу

Оскільки я зосередився лише на тих ділянках, де мав проблеми з робочим процесом, я вирішив поділитися повним скриптом файлу робочого процесу GitHub Actions після внесення необхідних виправлень:

name: Build & Deploy  
on:  
 push:  
 branches: [main]  

jobs:  
 build:  
 name: Build  
 runs-on: ubuntu-latest  
 steps:  
 - name: Checkout Code  
 uses: actions/checkout@v3  

 - name: Setup .NET  
 uses: actions/setup-dotnet@v3  
 with:  
 dotnet-version: '8.0.x'  

 - name: Restore Dependencies  
 run: dotnet restore CompanyName.ProductName.sln   

 - name: Build Solution  
 run: dotnet build CompanyName.ProductName.sln -c Release --verbosity minimal --no-restore  

 - name: Publish API  
 id: publish_api  
 run: |  
 API_PROJECT_PATH="CompanyName.ProductName.API"  
 PUBLISH_DIR="$(pwd)/$API_PROJECT_PATH/publish" # Явно задаємо шлях публікації  
 dotnet publish $API_PROJECT_PATH/CompanyName.ProductName.API.csproj -c Release --no-build --no-restore --property:PublishDir=$PUBLISH_DIR  
 echo "publish_path=$PUBLISH_DIR" >> $GITHUB_ENV  

 - name: Upload Artifact  
 uses: actions/upload-artifact@v3  
 with:  
 name: published-app  
 path: ./publish/  

 deploy:  
 name: Deploy Web API  
 needs: build  
 runs-on: ubuntu-latest  
 steps:  
 - name: Download Artifact  
 uses: actions/download-artifact@v3  
 with:  
 name: published-app  
 path: ./publish  

 - name: Transfer Files to Remote Server  
 uses: appleboy/[email protected]  
 with:  
 source: ./publish/*  
 target: /my/full/application/path/  
 host: ${{ secrets.SSH_HOST }}  
 username: ${{ secrets.SSH_USER }}  
 key: ${{ secrets.SSH_KEY }}  
 passphrase: ${{ secrets.SSH_PASSPHRASE }}  
 overwrite: true  

 - name: Restart Web API Service  
 uses: appleboy/[email protected]  
 with:  
 host: ${{ secrets.SSH_HOST }}  
 key: ${{ secrets.SSH_KEY }}  
 username: ${{ secrets.SSH_USER }}  
 passphrase: ${{ secrets.SSH_PASSPHRASE }}  
 script: |  
 sudo chown -R www-data:www-data /my/full/application/path/  
 sudo systemctl restart apiservice

Ключові висновки

  1. Захищайте ваші секрети: Завжди використовуйте GitHub Secrets для керування чутливими даними в робочих процесах.
  2. Явно визначайте шляхи: Уникайте непорозумінь, явно визначаючи шляхи до файлів для кожного кроку.
  3. Обробляйте віддалені директорії: Переконайтесь, що цільові директорії для деплою створюються або очищаються за необхідності.

З цими виправленнями робочий процес тепер працює без проблем, дозволяючи автоматизувати деплой .NET Web API через GitHub Actions.

Перетинаючи межі нового року, давайте продовжувати ділитися знаннями і покращувати наші робочі процеси. Якщо ви зіткнулися з подібними проблемами або маєте питання, не соромтеся ділитися ними в коментарях. Давайте розвиватися разом у 2025 році!

Перекладено з: Resolving CI/CD Workflow Issues with GitHub Actions for API Deployment to a VPS

Leave a Reply

Your email address will not be published. Required fields are marked *