В одном из моих проектов требуется автоматически выгружать код из ветки master
в production
после выполнения всех тестов.
К сожалению, GitLab CI не позволяет это сделать напрямую из скрипта без дополнительных настроек, так как токен, которым пользуется Runner, позволяет только читать из репозитория, но не писать в него.
Настройки для того чтобы открыть раннеру доступ на запись, в гитлабе нет.
Поэтому выкручиваемся.
Мы обратимся по SSH к гитлабу и выполним слияние веток.
Но в подключении по SSH из пайплайна GitLab есть парочка подводных камней, поэтому я пишу здесь подробно, как это сделать.
1. Создаём пару ключей:
ssh-keygen -t rsa
nex@Pacman3:~$ ssh-keygen -t rsa
Generating public/private rsa key pair.
Enter file in which to save the key (/home/nex/.ssh/id_rsa): gitlab_ci_private_key
Enter passphrase (empty for no passphrase):
Enter same passphrase again:
Your identification has been saved in gitlab_ci_private_key
Your public key has been saved in gitlab_ci_private_key.pub
The key fingerprint is:
SHA256:uMe8BGvC4N7ett8Q4BheH1nF9sQieEj4yITVAGxuitQ nex@Pacman3
The key's randomart image is:
+---[RSA 3072]----+
| ..+o=.o.o.. |
| + o +oo + o |
| .o.oooo. o + |
| . Eo=o+.. . |
|...oo + S |
|...o * . |
| . o + * |
| . . +.o + |
| ..o.ooo . |
+----[SHA256]-----+
2. Загружаем приватный ключ gitlab_ci_private_key
в переменную SSH_PRIVATE_KEY
:
GitLab -> My Project -> Settings -> CI / CD -> Variables -> Expand -> Add variable
3. Загружаем публичный ключ gitlab_ci_private_key.pub
в настройки репозитория.
GitLab -> My Project -> Settings -> Repository -> Deploy Keys -> Expand -> Add key
4. Используем следующие команды в .gitlab-ci.yml
:
Отмечу, что контейнер каждый раз создаётся “чистый”, и по SSH к незнакомому хосту просто так не подключится.
Поэтому заранее записываем хост гитлаба в файл known_hosts
.
- mkdir -p ~/.ssh
- echo "$SSH_PRIVATE_KEY" | tr -d '\r' > ~/.ssh/id_rsa
- chmod 600 ~/.ssh/id_rsa
- ssh-keyscan -t rsa gitlab.com >> ~/.ssh/known_hosts
...
- git remote show origin
- git remote set-url --push origin git@$CI_SERVER_HOST:$CI_PROJECT_PATH
- git remote show origin
- git checkout master-test-ci
- git pull
- git checkout production-test-ci
- git pull
- git merge master-test-ci
- git push --follow-tags origin HEAD:$CI_COMMIT_REF_NAME
Итог
Наш пайплайн обращается к гитлабу, выполняет тесты, делает слияние веток.