» » » Настройка GitLab CI для загрузки java проекта в maven central

 

Настройка GitLab CI для загрузки java проекта в maven central

Автор: admin от 26-04-2019, 18:15, посмотрело: 114

Данная статья рассчитана на java разработчиков, у которых возникла потребность быстро публиковать свои продукты в репозиториях sonatype и/или maven central с использованием GitLab. В данной статье я расскажу про настройку gitlab-runner, gitlab-ci и maven-plugin для решения данной задачи.

Общая информация
  • Настройка deploy роекта в GitLab

  • GitLab Runner


  • GitLab CI


  • Конфигурация pom.xml


  • Результат


  • Заключение



  • данной статье пользователем Googolplex, поэтому в нужных местах буду ссылаться на данную статью.
  • Предварительно регистрируемся в Sonatype JIRA и заводим тикет на открытие репозитория (более подробно читать раздел Создаём тикет на Sonatype JIRA). После открытия репозитория пара логин/пароль от JIRA (далее учетная запись Sonatype) будет использоваться для загрузки артефактов в Sonatype nexus.

  • Далее процесс генерации GPG ключа описан весьма сухо. Более подробно смотреть раздел Настройка GnuPG для подписи артефактов

  • Если вы используете Linux консоль для генерации GPG ключа (gnupg/gnupg2), то необходимо установить rng-tools для генерации энтропии. В противном случае генерация ключа может проходить очень долго.

  • Сервисы хранения [b]публичных[/b] GPG ключей




  • К содержанию



    deploy
  • После создания репозитория, необходимо ограничить доступ на изменение репозитория.

    Переходим в проект Settings Repository Protected Branches. Удаляем все правила и добавляем единственное правило с Wildcard * с правом на push и merge только для пользователей с ролью Maintainers. Данное правило будет работать для всех пользователей как данного проекта, так и группы в которую данный проект входит.

    Настройка GitLab CI для загрузки java проекта в maven central

  • Если мейнтейнеров несколько, то лучшим решением будет ограничить доступ к проекту в принципе.

    Переходим в проект Settings General Visibility, project features, permissions и выставляем Project visibility в значение [b]Private[/b].

    У меня проект в публичном доступе, так как я использую собственный GitLab Runner и доступ на изменение репозитория есть только у меня. Ну и собственно не в моих интересах светить приватную информацию в публичных pipeline-логах.

  • Ужесточение правил на изменение репозитория

    Переходим в проект Settings Repository Push Rules и устанавливаем флаги Committer restriction, Check whether author is a GitLab user. Так же рекомендую настроить подпись коммитов, и установить флаг Reject unsigned commits.

  • Далее требуется настроить триггер для запуска задач

    Переходим в проект Settings CI / CD Pipeline triggers и создаем новый trigger-token

    Данный токен можно сразу добавить в общую конфигурацию переменных для группы проектов.

    Переходим в группу Settings CI / CD Variables и добавляем переменную DEPLOY_TOKEN с trigger-token в значении.



  • К содержанию



    К содержанию



    Настройка GitLab CI для загрузки java проекта в maven central

    [/spoiler]


    • Регистрируем раннер



      gitlab-runner register --config /etc/gitlab-runner/gitlab-deployer-config.toml


    [spoiler=Процесс]
    Runtime platform arch=amd64 os=linux pid=17594 revision=3001a600 version=11.10.0
    Running in system-mode.
    Please enter the gitlab-ci coordinator URL (e.g. https://gitlab.com/):
    https://gitlab.com/
    Please enter the gitlab-ci token for this runner:
    REGISTRATION_TOKEN
    Please enter the gitlab-ci description for this runner:
    [ih1174328.vds.myihor.ru]: Deploy Runner
    Please enter the gitlab-ci tags for this runner (comma separated):
    deploy
    Registering runner... succeeded                     runner=ZvKdjJhx
    Please enter the executor: docker-ssh, parallels, virtualbox, docker-ssh+machine, kubernetes, docker, ssh, docker+machine, shell:
    shell
    Runner registered successfully. Feel free to start it, but if it's running already the config should be automatically reloaded!
    [/spoiler]

    • Проверяем, что раннер зарегистрирован. Переходим на сайт gitlab.com deploy-project Settings CI/CD Runners Specific Runners Runners activated for this project


    [spoiler=Скрин]

    Настройка GitLab CI для загрузки java проекта в maven central

    [/spoiler]

    • Добавляем [b]отдельный[/b] сервис /etc/systemd/system/gitlab-deployer.service

      [Unit]
      Description=GitLab Deploy Runner
      After=syslog.target network.target
      ConditionFileIsExecutable=/usr/local/bin/gitlab-runner
      [Service]
      StartLimitInterval=5
      StartLimitBurst=10
      ExecStart=/usr/local/bin/gitlab-runner "run" "--working-directory" "/home/gitlab-deployer" "--config" "/etc/gitlab-runner/gitlab-deployer-config.toml" "--service" "gitlab-deployer" "--syslog" "--user" "gitlab-deployer"
      Restart=always
      RestartSec=120
      [Install]
      WantedBy=multi-user.target

    • Запускаем сервис.

      systemctl enable gitlab-deployer.service
      systemctl start gitlab-deployer.service
      systemctl status gitlab-deployer.service

    • Проверяем, что раннер запущен.


    [spoiler=Пример]

    Настройка GitLab CI для загрузки java проекта в maven central

    [/spoiler]

    К содержанию


    К содержанию


    GitLab CI


    К содержанию


    Настройка GitLab CI для загрузки java проекта в maven central




    К содержанию


    К содержанию


    К содержанию


    К содержанию


    gitlab-ci в котором разместил шаблон CI для java проектов common.yml.


    common.yml[/b]
    stages:
      - build
      - test
      - verify
      - deploy
    
    variables:
      SONAR_ARGS: "
      -Dsonar.gitlab.commit_sha=${CI_COMMIT_SHA} 
      -Dsonar.gitlab.ref_name=${CI_COMMIT_REF_NAME} 
      "
    
    .build_java_project:
      stage: build
      tags:
        - touchbit-shell
      variables:
        SKIP_TEST: "false"
      script:
        - mvn clean
        - mvn package -DskipTests=${SKIP_TEST}
      artifacts:
        when: always
        expire_in: 30 day
        paths:
          - "*/target/reports"
    
    .build_sphinx_doc:
      stage: build
      tags:
        - touchbit-shell
      variables:
        DOCKERFILE: .indirect/docs/Dockerfile
      script:
        - docker build --no-cache -t ${CI_PROJECT_NAME}/doc -f ${DOCKERFILE} .
    
    .junit_module_test_run:
      stage: test
      tags:
        - touchbit-shell
      variables:
        MODULE: ""
      script:
        - cd ${MODULE}
        - mvn test
      artifacts:
        when: always
        expire_in: 30 day
        paths:
          - "*/target/reports"
    
    .junit_test_run:
      stage: test
      tags:
        - touchbit-shell
      script:
        - mvn test
      artifacts:
        when: always
        expire_in: 30 day
        paths:
        - "*/target/reports"
    
    .sonar_review:
      stage: verify
      tags:
        - touchbit-shell
      dependencies: []
      script:
        - >
          if [ "$CI_BUILD_REF_NAME" == "master" ]; then
            mvn compile sonar:sonar -Dsonar.login=$SONAR_LOGIN $SONAR_ARGS
          else
            mvn compile sonar:sonar -Dsonar.login=$SONAR_LOGIN $SONAR_ARGS -Dsonar.analysis.mode=preview
          fi
    
    .trigger_deploy:
      stage: deploy
      tags:
        - touchbit-shell
      variables:
        URL: "https://gitlab.com/api/v4/projects/10345765/trigger/pipeline"
        POST_DATA: "
          token=${DEPLOY_TOKEN}&
          ref=master&
          variables[DEPLOY]=${DEPLOY}&
          variables[DEPLOY_CI_REPOSITORY_URL]=${CI_REPOSITORY_URL}&
          variables[DEPLOY_CI_PROJECT_NAME]=${CI_PROJECT_NAME}&
          variables[DEPLOY_CI_COMMIT_SHA]=${CI_COMMIT_SHA}&
          variables[DEPLOY_CI_COMMIT_TAG]=${CI_COMMIT_TAG}
          "
      script:
      - wget --content-on-error -qO- ${URL} --post-data ${POST_DATA}
    
    .trigger_release_deploy:
      extends: .trigger_deploy
      only:
        - tags
    
    .trigger_snapshot_deploy:
      extends: .trigger_deploy
      when: manual
      except:
        - tags
    
    [/spoiler]

    В результате в самих java проектах .gitlab-ci.yml выглядит весьма компактно и не многословно


    [spoiler=.gitlab-ci.yml]
    include: https://gitlab.com/TouchBIT/gitlab-ci/raw/master/common.yml
    
    Shields4J:
      extends: .build_java_project
    
    Sphinx doc:
      extends: .build_sphinx_doc
      variables:
        DOCKERFILE: .docs/Dockerfile
    
    Sonar review:
      extends: .sonar_review
      dependencies:
        - Shields4J
    
    Release:
      extends: .trigger_release_deploy
    
    Snapshot:
      extends: .trigger_snapshot_deploy
    [/spoiler]

    К содержанию


    Googolplex в Настройка мавена для автоматической подписи и загрузки артефактов в snapshot- и staging-репозитории, поэтому я опишу некоторые нюансы использования плагинов. Так же я опишу как легко и непринужденно можно использовать nexus-staging-maven-plugin, если вы не хотите или не можете использовать org.sonatype.oss:oss-parent в качестве родителя для своего проекта.


    К содержанию


    К содержанию


    К содержанию


    staging репозитории


    <repositories>
      <repository>
        <id>SonatypeNexus</id>
        <url>https://oss.sonatype.org/content/groups/staging/</url>
        <!-- Не надо указывать флаги snapshot/release для репозитория -
      </repository>
    </repositories>

    Еще плюсы



    • Очень богатый список целей для работы с nexus репозиторием (mvn help:describe -Dplugin=org.sonatype.plugins:nexus-staging-maven-plugin).

    • Автоматическая проверка релиза на возможность загрузки в maven central


    К содержанию


    Настройка GitLab CI для загрузки java проекта в maven central


    При запуске данной задачи триггерится соответствующая задача в проекте deploy (пример).


    [spoiler=Подрезанный лог]
    Running with gitlab-runner 11.10.0 (3001a600)
      on Deploy runner JSKWyxUw
    Using Shell executor...
    Running on ih1174328.vds.myihor.ru...
    Skipping Git repository setup
    Skipping Git checkout
    Skipping Git submodules setup
    $ rm -rf .* *
    $ git config --global credential.helper store
    $ echo "https://gitlab-ci-token:${CI_JOB_TOKEN}@gitlab.com"  ~/.git-credentials
    $ git clone ${DEPLOY_CI_REPOSITORY_URL} .
    Cloning into 'shields4j'...
    $ git checkout ${DEPLOY_CI_COMMIT_SHA}
    Note: checking out '850f86aa317194395c5387790da1350e437125a7'.
    You are in 'detached HEAD' state. You can look around, make experimental
    changes and commit them, and you can discard any commits you make in this
    state without impacting any branches by performing another checkout.
    If you want to create a new branch to retain commits you create, you may
    do so (now or later) by using -b with the checkout command again. Example:
      git checkout -b new_branch_name
    HEAD is now at 850f86a... skip deploy test-core
    $ for pom in $(find . -name pom.xml); do # collapsed multi-line command
    $ if [[ "${DEPLOY_CI_COMMIT_TAG}" != "" ]]; then # collapsed multi-line command
    [INFO] Scanning for projects...
    [INFO] Inspecting build with total of 4 modules...
    [INFO] Installing Nexus Staging features:
    [INFO]   ... total of 4 executions of maven-deploy-plugin replaced with nexus-staging-maven-plugin
    [INFO] ------------------------------------------------------------------------
    [INFO] Reactor Build Order:
    [INFO] 
    [INFO] Shields4J                                                          [pom]
    [INFO] test-core                                                          [jar]
    [INFO] Shields4J client                                                   [jar]
    [INFO] TestNG listener                                                    [jar]
    [INFO] 
    [INFO] --------------< org.touchbit.shields4j:shields4j-parent >---------------
    [INFO] Building Shields4J 1.0.0                                           [1/4]
    [INFO] --------------------------------[ pom ]---------------------------------
    [INFO] 
    [INFO] --- versions-maven-plugin:2.5:set (default-cli) @ shields4j-parent ---
    [INFO] Searching for local aggregator root...
    [INFO] Local aggregation root: /home/gitlab-deployer/JSKWyxUw/0/TouchBIT/deploy/shields4j
    [INFO] Processing change of org.touchbit.shields4j:shields4j-parent:1.0.0  1.0.0-SNAPSHOT
    [INFO] Processing org.touchbit.shields4j:shields4j-parent
    [INFO]     Updating project org.touchbit.shields4j:shields4j-parent
    [INFO]         from version 1.0.0 to 1.0.0-SNAPSHOT
    [INFO] 
    [INFO] Processing org.touchbit.shields4j:client
    [INFO]     Updating parent org.touchbit.shields4j:shields4j-parent
    [INFO]         from version 1.0.0 to 1.0.0-SNAPSHOT
    [INFO]     Updating dependency org.touchbit.shields4j:test-core
    [INFO]         from version 1.0.0 to 1.0.0-SNAPSHOT
    [INFO] 
    [INFO] Processing org.touchbit.shields4j:test-core
    [INFO]     Updating parent org.touchbit.shields4j:shields4j-parent
    [INFO]         from version 1.0.0 to 1.0.0-SNAPSHOT
    [INFO] 
    [INFO] Processing org.touchbit.shields4j:testng
    [INFO]     Updating parent org.touchbit.shields4j:shields4j-parent
    [INFO]         from version 1.0.0 to 1.0.0-SNAPSHOT
    [INFO]     Updating dependency org.touchbit.shields4j:client
    [INFO]         from version 1.0.0 to 1.0.0-SNAPSHOT
    [INFO]     Updating dependency org.touchbit.shields4j:test-core
    [INFO]         from version 1.0.0 to 1.0.0-SNAPSHOT
    [INFO] 
    [INFO] ------------------------------------------------------------------------
    [INFO] Reactor Summary:
    [INFO] 
    [INFO] Shields4J 1.0.0 .................................... SUCCESS [  0.992 s]
    [INFO] test-core .......................................... SKIPPED
    [INFO] Shields4J client ................................... SKIPPED
    [INFO] TestNG listener 1.0.0 .............................. SKIPPED
    [INFO] ------------------------------------------------------------------------
    [INFO] BUILD SUCCESS
    [INFO] ------------------------------------------------------------------------
    [INFO] Total time: 2.483 s
    [INFO] Finished at: 2019-04-21T02:40:42+03:00
    [INFO] ------------------------------------------------------------------------
    $ mvn clean deploy -DskipTests=${SKIP_TESTS}
    [INFO] Scanning for projects...
    [INFO] Inspecting build with total of 4 modules...
    [INFO] Installing Nexus Staging features:
    [INFO]   ... total of 4 executions of maven-deploy-plugin replaced with nexus-staging-maven-plugin
    [INFO] ------------------------------------------------------------------------
    [INFO] Reactor Build Order:
    [INFO] 
    [INFO] Shields4J                                                          [pom]
    [INFO] test-core                                                          [jar]
    [INFO] Shields4J client                                                   [jar]
    [INFO] TestNG listener                                                    [jar]
    [INFO] 
    [INFO] --------------< org.touchbit.shields4j:shields4j-parent >---------------
    [INFO] Building Shields4J 1.0.0-SNAPSHOT                                  [1/4]
    [INFO] --------------------------------[ pom ]---------------------------------
    ...
    DELETED
    ...
    [INFO]  * Bulk deploy of locally gathered snapshot artifacts finished.
    [INFO] Remote deploy finished with success.
    [INFO] ------------------------------------------------------------------------
    [INFO] Reactor Summary:
    [INFO] 
    [INFO] Shields4J 1.0.0-SNAPSHOT ........................... SUCCESS [  2.375 s]
    [INFO] test-core .......................................... SUCCESS [  3.929 s]
    [INFO] Shields4J client ................................... SUCCESS [  3.815 s]
    [INFO] TestNG listener 1.0.0-SNAPSHOT ..................... SUCCESS [ 36.134 s]
    [INFO] ------------------------------------------------------------------------
    [INFO] BUILD SUCCESS
    [INFO] ------------------------------------------------------------------------
    [INFO] Total time: 47.629 s
    [INFO] Finished at: 2019-04-21T02:41:32+03:00
    [INFO] ------------------------------------------------------------------------
    [/spoiler]

    В результате в nexus загружена версия 1.0.0-SNAPSHOT.


    Все snapshot версси можно удалить из репозитория на сайте oss.sonatype.org под своей учетной записью.


    Настройка GitLab CI для загрузки java проекта в maven central


    К содержанию


    пример).


    Настройка GitLab CI для загрузки java проекта в maven central


    Самое приятное, что автоматически срабатывает close release в nexus.


    [INFO] Performing remote staging...
    [INFO] 
    [INFO]  * Remote staging into staging profile ID "9043b43f77dcc9"
    [INFO]  * Created staging repository with ID "orgtouchbit-1037".
    [INFO]  * Staging repository at https://oss.sonatype.org:443/service/local/staging/deployByRepositoryId/orgtouchbit-1037
    [INFO]  * Uploading locally staged artifacts to profile org.touchbit
    [INFO]  * Upload of locally staged artifacts finished.
    [INFO]  * Closing staging repository with ID "orgtouchbit-1037".
    Waiting for operation to complete...
    .........
    [INFO] Remote staged 1 repositories, finished with success.
    [INFO] ------------------------------------------------------------------------
    [INFO] Reactor Summary:
    [INFO] 
    [INFO] Shields4J 1.0.0 .................................... SUCCESS [  9.603 s]
    [INFO] test-core .......................................... SUCCESS [  3.419 s]
    [INFO] Shields4J client ................................... SUCCESS [  9.793 s]
    [INFO] TestNG listener 1.0.0 .............................. SUCCESS [01:23 min]
    [INFO] ------------------------------------------------------------------------
    [INFO] BUILD SUCCESS
    [INFO] ------------------------------------------------------------------------
    [INFO] Total time: 01:47 min
    [INFO] Finished at: 2019-04-21T04:05:46+03:00
    [INFO] ------------------------------------------------------------------------

    [spoiler=И если что-то пошло не так, то задача обязательно завалится]
    [INFO] Performing remote staging...
    [INFO] 
    [INFO]  * Remote staging into staging profile ID "9043b43f77dcc9"
    [INFO]  * Created staging repository with ID "orgtouchbit-1038".
    [INFO]  * Staging repository at https://oss.sonatype.org:443/service/local/staging/deployByRepositoryId/orgtouchbit-1038
    [INFO]  * Uploading locally staged artifacts to profile org.touchbit
    [INFO]  * Upload of locally staged artifacts finished.
    [INFO]  * Closing staging repository with ID "orgtouchbit-1038".
    Waiting for operation to complete...
    .......
    [ERROR] Rule failure while trying to close staging repository with ID "orgtouchbit-1039".
    [ERROR] 
    [ERROR] Nexus Staging Rules Failure Report
    [ERROR] ==================================
    [ERROR] 
    [ERROR] Repository "orgtouchbit-1039" failures
    [ERROR]   Rule "signature-staging" failures
    [ERROR]     * No public key: Key with id: (1f42b618d1cbe1b5) was not able to be located on [leech=http://keys.gnupg.net:11371/]. Upload your public key and try the operation again.
    ...
    [ERROR] Cleaning up local stage directory after a Rule failure during close of staging repositories: [orgtouchbit-1039]
    [ERROR]  * Deleting context 9043b43f77dcc9.properties
    [ERROR] Cleaning up remote stage repositories after a Rule failure during close of staging repositories: [orgtouchbit-1039]
    [ERROR]  * Dropping failed staging repository with ID "orgtouchbit-1039" (Rule failure during close of staging repositories: [orgtouchbit-1039]).
    [ERROR] Remote staging finished with a failure: Staging rules failure!
    [INFO] ------------------------------------------------------------------------
    [INFO] Reactor Summary:
    [INFO] 
    [INFO] Shields4J 1.0.0 .................................... SUCCESS [  4.073 s]
    [INFO] test-core .......................................... SUCCESS [  2.788 s]
    [INFO] Shields4J client ................................... SUCCESS [  3.962 s]
    [INFO] TestNG listener 1.0.0 .............................. FAILURE [01:07 min]
    [INFO] ------------------------------------------------------------------------
    [INFO] BUILD FAILURE
    [INFO] ------------------------------------------------------------------------
    [/spoiler]

    В резултате нам остается единственный выбор. Или удалить данную версию или опубликовать.



    Настройка GitLab CI для загрузки java проекта в maven central[/leech]



    После релиза, через некоторое время артефакты окажутся в [img]https://maven-badges.herokuapp.com/maven-central/org.touchbit.shields4j/shields4j-parent/badge.svg?style=plastic[/img]



    [spoiler=офтоп]

    Для меня было открытием, что maven индексирует другие публичные репозитории.

    Пришлось подкинуть robots.txt, так как он проиндексировал мой старый репозиторий.

    [/spoiler]

    К содержанию



    К содержанию



    Источник: Хабр / Интересные публикации

    Категория: Яндекс

    Уважаемый посетитель, Вы зашли на сайт как незарегистрированный пользователь.
    Мы рекомендуем Вам зарегистрироваться либо войти на сайт под своим именем.

    Добавление комментария

    Имя:*
    E-Mail:
    Комментарий:
    Полужирный Наклонный текст Подчеркнутый текст Зачеркнутый текст | Выравнивание по левому краю По центру Выравнивание по правому краю | Вставка смайликов Выбор цвета | Скрытый текст Вставка цитаты Преобразовать выбранный текст из транслитерации в кириллицу Вставка спойлера
    Введите два слова, показанных на изображении: *