Сервис:
gitlab.4gain.pro(gitlab). Compose-стек на firefly. Backup → annalium weekly Sun 04:00 MSK.
gitlab-backup создаётся под конкретную major.minor.patch. Restore из 14.2.7 backup на 14.3 / 15.x — НЕ работает напрямую (нужен upgrade-path с промежуточными версиями).gitlab-secrets.json шифрует поля БД (CI vars, runner-токены, LDAP-creds). Без него — БД восстановится, но encrypted поля будут unreadable; runner'ы перестанут работать; CI variables потеряются.gitlab.rb — конфиг (external_url, SMTP, omniauth, лимиты). Без него — рестор поднимется на default-конфиге, придётся пере-настраивать.backup-gitlab.timer запускает скрипт Sun 04:00 MSK (еженедельно, gitlab-backup ёмкий).
Что попадает на annalium /mnt/storage/firefly-backup/gitlab/:
| Файл | Что |
|---|---|
<TS>_gitlab_backup.tar |
Output от gitlab-backup create — репо, БД, LFS, uploads, builds, artifacts, ci_secure_files, registry, pages, packages, terraform_state |
<TS>_config.tar.gz |
/etc/gitlab/{gitlab.rb,gitlab-secrets.json} — обязательно для рестора |
<TS> = 1714543200_2026_05_03_14.2.7-ee (timestamp + дата + version).
Retention: локально на firefly keep last 3 (/mnt/compose/gitlab/data/gitlab/volumes/data/backups/), на annalium 30 дней.
cd ansible/playbooks
ansible-playbook -c ssh service-gitlab-backup.yml -e sm2c_backup_gitlab_run_now=true
# Или прямо на firefly
ssh -p 21150 root@firefly.e1.4gain.pro 'systemctl start backup-gitlab.service'
journalctl -u backup-gitlab -f
Backup занимает 10–60 мин в зависимости от размера репо/БД/LFS.
ssh -p 21150 root@firefly.e1.4gain.pro
TS=$(date +%s_%Y_%m_%d_14.2.7-ee)
tar -czf /tmp/${TS}_config.tar.gz \
-C /mnt/compose/gitlab/data/gitlab/volumes/config \
gitlab.rb gitlab-secrets.json
scp /tmp/${TS}_config.tar.gz root@10.19.1.13:/mnt/storage/firefly-backup/gitlab/
ssh root@10.19.1.13 'ls -lh /mnt/storage/firefly-backup/gitlab/ | tail -6'
Предусловия:
gitlab.4gain.pro, registry.4gain.pro, pages.4gain.pro → IP firefly.gitlab/gitlab-ee:14.2.7-ee.0).Шаги:
# 1. Поднять чистый стек GitLab без данных
cd ansible/playbooks
ansible-playbook -c ssh service-gitlab-bootstrap.yml
# Подождать 5–10 мин пока gitlab инициализируется (миграции БД)
ssh -p 21150 root@firefly.e1.4gain.pro 'docker logs gitlab --tail 5'
# Когда увидим "gitlab Reconfigured" — готово.
# 2. Восстановить config + secrets ПЕРВЫМ (gitlab-secrets шифрует БД)
ssh -p 21150 root@firefly.e1.4gain.pro
cd /tmp
scp root@10.19.1.13:/mnt/storage/firefly-backup/gitlab/<TS>_config.tar.gz .
tar -xzf <TS>_config.tar.gz \
-C /mnt/compose/gitlab/data/gitlab/volumes/config
chmod 600 /mnt/compose/gitlab/data/gitlab/volumes/config/gitlab-secrets.json
docker exec gitlab gitlab-ctl reconfigure # применить gitlab.rb
docker restart gitlab
# Подождать пока снова поднимется (~3 мин)
# 3. Скопировать backup-tar в /var/opt/gitlab/backups (внутри контейнера)
scp root@10.19.1.13:/mnt/storage/firefly-backup/gitlab/<TS>_gitlab_backup.tar \
/mnt/compose/gitlab/data/gitlab/volumes/data/backups/
# Permissions важны:
chown 998:998 /mnt/compose/gitlab/data/gitlab/volumes/data/backups/<TS>_gitlab_backup.tar
chmod 600 /mnt/compose/gitlab/data/gitlab/volumes/data/backups/<TS>_gitlab_backup.tar
# 4. Остановить процессы которые пишут в БД
docker exec -it gitlab gitlab-ctl stop unicorn puma sidekiq
# 5. Запустить restore (BACKUP=<TS> без _gitlab_backup.tar суффикса)
docker exec -it gitlab gitlab-backup restore BACKUP=<TS> force=yes
# Будут вопросы про authorized_keys и БД — отвечать `yes`. Длится 10–60 мин.
# 6. Reconfigure + start
docker exec gitlab gitlab-ctl reconfigure
docker exec gitlab gitlab-ctl restart
docker exec gitlab gitlab-rake gitlab:check SANITIZE=true
# 7. Проверка
curl -kI https://gitlab.4gain.pro/
# → 302 → /users/sign_in
ssh -p 21150 root@firefly.e1.4gain.pro
scp root@10.19.1.13:/mnt/storage/firefly-backup/gitlab/<TS>_config.tar.gz /tmp/
tar -xzf /tmp/<TS>_config.tar.gz \
-C /mnt/compose/gitlab/data/gitlab/volumes/config gitlab.rb
docker exec gitlab gitlab-ctl reconfigure
GitLab не имеет встроенной команды для restore одного репо из tarball. Альтернатива:
# Извлечь только нужный репо из backup-tar (это nested tar)
mkdir /tmp/gitlab-extract && cd /tmp/gitlab-extract
tar -xf /mnt/compose/gitlab/data/gitlab/volumes/data/backups/<TS>_gitlab_backup.tar
ls # должны увидеть repositories.tar.gz, db/, и т.д.
tar -tzf repositories.tar.gz | grep '<group>/<project>'
tar -xzf repositories.tar.gz '<group>/<project>.bundle'
# Создать новый/пустой репо в gitlab UI с тем же path
# Затем git push --mirror на этот repo:
git clone --mirror <group>/<project>.bundle <project>
cd <project>
git remote set-url origin git@gitlab.4gain.pro:<group>/<project>.git
git push --mirror
GitLab требует последовательный апгрейд через major.minor versions. Backup из 14.2.7 → 17.x не работает напрямую.
Стандартный путь:
⚠ Это многочасовая процедура. Лучше держать backup в актуальной версии с момента upgrade.
| Симптом | Причина | Решение |
|---|---|---|
gitlab-backup restore падает на decrypt failed |
gitlab-secrets.json не восстановлен / другой | Восстановить config tar.gz из того же <TS> |
| Runner'ы не могут зарегистрироваться после restore | runner.token шифруется secrets'ами; если new server has different secrets, токены invalid | Re-register runner с new token из gitlab UI → docker exec gitlab_runner_<NN> gitlab-runner register |
| После restore CI variables не дешифруются | gitlab-secrets.json подменили / потерян |
Перезаписать в UI |
| Pages не работает | Volume mount gitlab-pages пустой, или wrong domain |
Проверить pages.4gain.pro → IP, gitlab-pages env в compose, pages_external_url в gitlab.rb |
gitlab_pages в Restarting, лог GitLab API URL or API secret has not been provided |
compose-команда не передаёт -config / -api-secret-key (с pages 1.42+ обязательно) |
См. фикс ниже |
gitlab_pages лог connect: connection refused ... :443 |
pages пытается HTTPS к gitlab внутри docker network, gitlab слушает HTTP | Добавить -internal-gitlab-server http://gitlab в command: pages |
| Pages volumes пусты после deploy | Compose-файл лежит в symlink — relative paths резолвятся не там где данные | Положить compose-файл в реальный каталог (где живёт ./volumes/) |
gitlab-rake gitlab:check ругается на repos |
Permissions битые | docker exec gitlab gitlab-ctl reconfigure обычно фиксит |
Pages с 1.42+ использует API-based domain config (вместо disk-based из старых версий). Нужны api-secret-key + gitlab-server. GitLab-omnibus генерит готовый /var/opt/gitlab/gitlab-pages/gitlab-pages-config при gitlab-ctl reconfigure — используем его:
pages:
image: gitlab/gitlab-ee:14.2.7-ee.0
...
command:
- -config
- /var/opt/gitlab/gitlab-pages/gitlab-pages-config
- -internal-gitlab-server
- http://gitlab # внутри docker network — HTTP, TLS делает traefik
volumes:
- './volumes/data/gitlab-pages:/var/opt/gitlab/gitlab-pages:rw'
- './volumes/data/gitlab-rails/shared/pages:/var/opt/gitlab/gitlab-rails/shared/pages:ro'
- './volumes/data/gitlab-rails/etc:/var/opt/gitlab/gitlab-rails/etc:ro' # .gitlab_pages_secret
ports:
- "0.0.0.0:82:8090" # omnibus default listen-proxy=:8090
Применено в sm2c-cloud-gitlab роли. См. также GitLab → Pages 1.42+.
Changelog