Рубрики
Без рубрики

Автоматическое развертывание приложения Spring Boot с помощью Gitlab CI/CD

Обзор В этой статье мы рассмотрим, как использовать Gitlab CI /CD для сборки,… С тегами spring boot, java, gitlab, digitalocean.

Обзор

В этой статье мы рассмотрим, как использовать Gitlab CI/CD для создания, тестирования и развертывания веб-приложения Spring Boot на экземпляре сервера.

Gitlab предлагает щедрое предложение неограниченных бесплатных частных репозиториев и 2000 минут CI/CD runner.

В этой статье мы будем использовать Gitlab в качестве нашего облачного репозитория Git, и мы рекомендуем вам создать учетную запись, если у вас ее еще нет.

Настройка приложения

Для целей этой статьи мы создадим простое приложение Spring Boot, используя Spring Initializr .

После загрузки сгенерированного проекта, pom.xml должно выглядеть так:

                                             
                                               
        org.springframework.boot        
        spring-boot-starter-web   
                                              

                                               
        org.springframework.boot        
        spring-boot-starter-test  
        test                                
                                              
                                            

Далее давайте создадим сопоставление контроллера для конечной точки индекса. Конечная точка просто вернет строку hello world, объединенную с текущей меткой времени:

@Controller                                           
public class IndexController {                        

    @GetMapping("/")                                  
    @ResponseBody                                     
    public String index() {                           
        return "Hello World " + LocalDateTime.now();  
    }                                                 

}

Мы можем протестировать новую конечную точку, запустив приложение и посетив http://localhost:8080 в вашем браузере мы должны увидеть строку hello world.

Теперь, когда у нас есть работающее приложение, нам нужно создать новый проект в Gitlab, зафиксировать наш код локально и отправить его в удаленное хранилище, используя URL-адрес проекта, сгенерированный Gitlab.

Давайте выполним следующие команды из корневого каталога проекта на вашем локальном компьютере:

git init

git add .

git commit -m "initial commit"

git remote add origin https://gitlab.com/SeunMatt/gitlab-ci-demo.git

git push origin master

Обратите внимание, что URL-адрес вашего проекта будет немного отличаться в зависимости от выбранного имени пользователя и названия проекта.

Настройка сервера

Для этого урока мы создадим новый DigitalOcean droplet, установим на него JRE (Java Runtime Environment) и Nginx.

Nginx будет служить обратным прокси-сервером, который будет работать на порту 80 и перенаправлять HTTP-трафик в наше приложение Spring Boot, которое будет работать на внутреннем порту 8080.

Мы будем использовать конфигурационные файлы Terraform из другой статьи для создания droplet.

Gitlab CI/CD

В этом разделе мы рассмотрим, как мы можем настроить Gitlab для автоматического развертывания нашего приложения Spring Boot всякий раз, когда мы вносим новые изменения.

Мы начнем с добавления .gitlab-ci.yml в ваш проект, затем создадим нового пользователя CI/CD на сервере и, наконец, определим наш конвейер с необходимыми скриптами.

Создание приложений

Чтобы мы могли использовать Gitlab CI/CD, нам нужно добавить файл .gitlab-ci.yml в корень нашего каталога проекта.

.gitlab-ci.yml – это простой текстовый файл, который определяет задания, которые мы хотим выполнить, и какие сценарии мы хотим запускать в каждом задании.

Давайте создадим файл .gitlab-ci.yml в корневом каталоге вашего проекта со следующим содержимым:

stages:
 - build
 - deploy

Приведенный выше фрагмент определяет два этапа, которые должны выполняться в том порядке, в котором они появляются.

Мы можем рассматривать этапы как группировку одного или нескольких заданий. Комбинация различных этапов образует конвейер.

Название каждого этапа должно отражать тип задания (заданий) на нем.

Например, на этапе сборки будут задания, которые тестируют и упаковывают наше приложение в виде jar-файла, тогда как этап развертывания будет содержать задания, которые копируют созданный jar-файл на сервер.

Давайте определим задание, которое будет запускать команду Maven package и генерировать один jar-файл. Мы будем называть задание maven-build:

maven-build:
  image: maven:3-jdk-11
  stage: build
  script: "mvn package -B"
  artifacts:
    paths:
      - target/gitlab-ci-demo.jar

В приведенном выше фрагменте мы настроили задание на использование контейнера docker, который содержит Maven версии 3 и JDK 11.

Ключевое слово stage указывает, что это задание относится к этапу сборки, а ключевое слово script указывает, какую команду выполнить в контейнере docker, как только он будет готов.

Еще одно особое ключевое слово, на которое следует обратить внимание, – это артефакты. Он инструктирует Gitlab CI/CD runner сохранить конечный результат нашей команды script, чтобы мы могли использовать его в последующих заданиях.

В этом случае мы сохраняем окончательный файл jar, чтобы мы могли ссылаться на него в следующих разделах.

Полный файл .gitlab-ci.yml выглядит следующим образом:

stages:                          
 - build                         
 - deploy                        

maven-build:                     
  image: maven:3-jdk-11          
  stage: build                   
  script: "mvn package -B"       
  artifacts:                     
    paths:                       
      - target/gitlab-ci-demo.jar

Чтобы увидеть это в действии, давайте зафиксируем и отправим наши изменения в Gitlab. Gitlab автоматически обнаружит файл .gitlab-ci.yml и запустит Gitlab CI/CD runner.

Мы можем отслеживать ход выполнения заданий в Gitlab, перейдя в меню CI/CD >> Задания:

Мы можем нажать на кнопку запуска, чтобы увидеть текущие результаты различных команд.

Как только сборка будет завершена, кнопка запуска изменится на зеленую, и теперь будет передан текст:

Развертывание приложений

Для нашего процесса развертывания мы сначала создадим пользователя CI/CD на нашем сервере, затем с помощью команды scp скопируем файл jar из Gitlab на наш сервер.

Как только файл jar окажется на нашем сервере, мы подключимся к серверу по ssh, переместим файл jar в соответствующий каталог и перезапустим службу приложений с помощью systemctl.

Давайте подключимся по SSH к экземпляру сервера, который мы подготовили ранее, и выполним следующие команды для создания и настройки пользователя CI/CD:

adduser --quiet --shell $SHELL --disabled-password --gecos 'GitlabCI User' gitlab-ci

usermod -a -G sudo gitlab-ci

echo 'gitlab-ci:changemepassword' | chpasswd

printf 'Match User gitlab-ci\n\tPasswordAuthentication yes\n' >> /etc/ssh/sshd_config

systemctl restart sshd

echo 'gitlab-ci ALL=(ALL) NOPASSWD: /bin/mv, NOPASSWD: /usr/bin/systemctl, NOPASSWD: /bin/cp' | sudo EDITOR='tee -a' visudo

Во-первых, мы создали нового пользователя gitlab-ci а затем мы меняем пароль пользователя на changeme password.

Затем мы обновили файл ssh_config, чтобы разрешить нашему новому пользователю проходить аутентификацию с помощью пароля, и перезапустили службу sshd.

Последняя команда очень важна, она отключает запрос пароля sudo, когда мы выполняем любую из следующих команд: mv, systemtctl и cp.

Нам нужно установить это, потому что мы будем использовать пользователя в автоматизированном процессе, лишенном вмешательства человека, для ввода пароля sudo.

Нам нужно добавить пароль gitlab-ci в качестве переменной среды в Gitlab, чтобы мы могли безопасно ссылаться на него в нашем файле .gitlab-ci.yml.

Чтобы сделать это, нам нужно войти в вашу учетную запись Gitlab >> Настройки >> CI/CD >> Переменные.

Как только мы развернем раздел Переменных, мы увидим кнопку для добавления новой переменной, мы должны нажать на нее, чтобы добавить переменную:

Теперь, когда мы создали нашего пользователя и добавили пароль пользователя в переменную CI/CD в Gitlab, давайте обновим наш файл .gitlab-ci.yml заданием deploy:

deploy-master:                                                                                                                                  
  before_script:                                                                                                                                
    - apt-get update -qq && apt-get install -y -qq sshpass                                                                                      
  stage: deploy                                                                                                                                 
  script:                                                                                                                                       
    - sshpass -V                                                                                                                                
    - export SSHPASS=$CI_USER_PASS                                                                                                              
    - sshpass -e scp -o StrictHostKeyChecking=no target/gitlab-ci-demo.jar gitlab-ci@167.172.188.139:/home/gitlab-ci                            
    - sshpass -e ssh -tt -o StrictHostKeyChecking=no gitlab-ci@167.172.188.139 sudo mv /home/gitlab-ci/gitlab-ci-demo.jar /opt/java/webapps     
    - sshpass -e ssh -tt -o StrictHostKeyChecking=no gitlab-ci@167.172.188.139 sudo systemctl restart gitlab-ci-demo.service                                                                                                                                                                 

В этом определении задания мы используем before_script, чтобы указать, какая команда должна быть выполнена на сервере перед выполнением других команд в теге script.

Кроме того, в разделе скрипта мы экспортировали пароль для пользователя CI в текущую среду как SSHPASS.

Таким образом, sshpass будет автоматически отвечать на запросы пароля из команд ssh и scp со значением переменной среды SSHPASS

Команды SSH, которые мы выполнили, довольно просты, сначала мы используем scp для копирования файла на сервер, а затем перемещаем файл в нужный каталог и, наконец, перезапускаем службу с помощью systemtctl.

Полный файл .gitlab-ci.yml будет иметь следующее содержимое:

stages:                                                                                                                                         
 - build                                                                                                                                        
 - deploy                                                                                                                                       

maven-build:                                                                                                                                    
  image: maven:3-jdk-11                                                                                                                         
  stage: build                                                                                                                                  
  script: "mvn package -B"                                                                                                                      
  artifacts:                                                                                                                                    
    paths:                                                                                                                                      
      - target/gitlab-ci-demo.jar                                                                                                               

deploy-master:                                                                                                                                  
  before_script:                                                                                                                                
    - apt-get update -qq && apt-get install -y -qq sshpass                                                                                      
  stage: deploy                                                                                                                                 
  script:                                                                                                                                       
    - sshpass -V                                                                                                                                
    - export SSHPASS=$CI_USER_PASS                                                                                                              
    - sshpass -e scp -o StrictHostKeyChecking=no target/gitlab-ci-demo.jar gitlab-ci@167.172.188.139:/home/gitlab-ci                            
    - sshpass -e ssh -tt -o StrictHostKeyChecking=no gitlab-ci@167.172.188.139 sudo mv /home/gitlab-ci/gitlab-ci-demo.jar /opt/java/webapps     
    - sshpass -e ssh -tt -o StrictHostKeyChecking=no gitlab-ci@167.172.188.139 sudo systemctl restart gitlab-ci-demo.service                    

Давайте зафиксируем наши изменения и будем продвигаться вперед. Как обычно, Gitlab автоматически запустит runner, и мы сможем следить за ходом конвейера.

Как только конвейер пройден, мы можем перейти к нашему домену/IP-адресу и увидеть, что наше веб-приложение запущено.

Дополнение

С учетом того, что мы настроили до сих пор, каждый раз, когда мы нажимаем на наш репозиторий git, Gitlab будет создавать и развертывать.

Что, если мы хотим, чтобы Gitlab развертывался только в том случае, если мы нажимаем на master? Мы можем легко добиться этого, добавив тег правил в deploy-master:

deploy-master:                                                                                                                              
  rules:                                                                                                                                    
    - if: '$CI_COMMIT_BRANCH =~ /^master$/'                                                                                                 
  before_script:                                                                                                                            
    - apt-get update -qq && apt-get install -y -qq sshpass                                                                                  
  stage: deploy                                                                                                                             
  script:                                                                                                                                   
    - sshpass -V                                                                                                                            
    - export SSHPASS=$CI_USER_PASS                                                                                                          
    - sshpass -e scp -o StrictHostKeyChecking=no target/gitlab-ci-demo.jar gitlab-ci@167.172.188.139:/home/gitlab-ci                        
    - sshpass -e ssh -tt -o StrictHostKeyChecking=no gitlab-ci@167.172.188.139 sudo mv /home/gitlab-ci/gitlab-ci-demo.jar /opt/java/webapps 
    - sshpass -e ssh -tt -o StrictHostKeyChecking=no gitlab-ci@167.172.188.139 sudo systemctl restart gitlab-ci-demo.service                

Таким образом, если мы перейдем к любой другой ветви, отличной от master, будет выполняться только задание maven-build.

Однако, если мы объединим или переместим в главную ветку, будут запущены как maven-build, так и deploy-master.

Вывод

В этой статье мы рассмотрели основы настройки конвейера CI/CD в Gitlab, и в процессе мы развернули простое приложение Spring Boot.

Gitlab CI/CD обладает большим количеством возможностей и функций, чем упомянутые, я рекомендую вам ознакомиться с официальной документацией , чтобы узнать больше. Полный исходный код доступен на Gitlab .

Оригинал: “https://dev.to/seunmatt/auto-deploy-spring-boot-app-using-gitlab-ci-cd-86b”