Ostatnio chciałem dokonać aktualizacji GitLab-a w moim domowym labie. Nie wyszło. Podnosząc wersję oprogramowania GitLab-a, od dwóch lat nie aktualizowałem wersji bazy danych, która jest niezbędna do prawidłowego działania. O ile wersja GitLab 13.1.4 nadal działała z PostgreSQL 9.6.2 (mimo że w dokumentacji jest zapisane, że to od dawna wersja niewspierana), to wersja 13.2 już ze starą bazą uruchomić się nie chciała. Aktualizacja bazy nigdy nie należy do prostych zadań. Pokażę Ci, w jaki sposób ja podszedłem do tego zadania i wykorzystałem dobrodziejstwo kontenerów. Nie jest to metoda zgodna z zaleceniami, które znajdziesz w dokumentacji, ale działa. I moim zdaniem do zastosowań w labie jest najprostsza i najszybsza. Aktualizacja kontenera bazy danych okazała się dzięki temu całkiem szybka i niezbyt skomplikowana.
Jak wygląda GitLab w kontenerach?
Zanim przejdziemy do tego, co musisz zrobić, słówko o tym, jak wygląda GitLab uruchamiany w kontenerach. Wiele osób odpala pojedynczy kontener z całym niezbędnym oprogramowaniem w środku. To błąd i wypaczenie idei konteneryzacji. W moim labie GitLab uruchamiany jest w trzech kontenerach – samo oprogramowanie (gitlab), baza danych (postgresql) oraz baza typu klucz-wartość (redis), która tak naprawdę nie jest używana.
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 643912c96826 gitlab/gitlab-ce:13.1.4-ce.0 "/assets/wrapper" 20 hours ago Up 20 hours (healthy) 0.0.0.0:80->80/tcp, 0.0.0.0:443->443/tcp, 0.0.0.0:30022->22/tcp gitlab-ce_gitlab_1 7d0a678ecb83 postgres:9.6.2-alpine "docker-entrypoint.s…" 20 hours ago Up 20 hours 5432/tcp gitlab-ce_postgresql_1 67b638c8d882 redis:3.0.7-alpine "docker-entrypoint.s…" 21 hours ago Up 20 hours 6379/tcp gitlab-ce_redis_1
Wersje każdego z komponentów są wymuszone statycznie poprzez odwołanie do odpowiedniej etykiety obrazu. Każdy z kontenerów ma też swój własny wolumen (typu persistent volume) na dane. Celem jest aktualizacja kontenera z bazą PostgreSQL z wersji 9.6.2-alpine do 12.3-alpine. Nie możemy tego jednak zrobić przez zwykłe uruchomienie obrazu w nowszej wersji . Baza danych się nie uruchomi. Zobaczymy błąd, który sygnalizuje nam niezgodność wersji samej bazy z wersją oprogramowania. Zatem musimy stworzyć nową bazę i przenieść do niej dane.
Pierwszym krokiem, zarówno bezpieczeństwa, jak i wymaganym do przeniesienia danych jest wykonanie kopii zapasowej bazy. Możemy to zrobić poleceniem docker-compose exec postgresql_1 pg_dumpall -U gitlab > dump.sql
albo korzystając z oprogramowania PgAdmin. Ja preferuję drugą metodę, gdyż łatwiej wtedy dane odtworzyć. Robimy backup jedynie bazy gitlabhq_production
.
Aby podłączyć się do bazy danych za pomocą PgAdmin, musimy port bazy danych udostępnić na hoście, na którym działa Docker modyfikując konfigurację kontenera w sekcji ports
. Ja wystawiłem na porcie hosta 35432, który połączony został z portem 5432 kontenera.
ports: - "35432:5432"
Jak przebiega aktualizacja kontenera bazy danych?
Gdybym miał w skrócie opisać jak wygląda aktualizacja kontenera bazy danych, to proces migracji przedstawiałby się on następująco:
- Tworzę kopię zapasową bazy gitlabhq_production
- Tworzę drugi kontener bazy danych korzystając z obrazu w wersji, do której chcę dokonać aktualizacji.
- Wiążę kontener z nową wersją bazy z kontenerem oprogramowania GitLab, odłączając jednocześnie starą wersję (bez kasowania danych z dysku)
- Uruchamiam stos z usługą GitLab
- Pozwalam, aby oprogramowanie GitLab zainicjowało nową bazę w przygotowanym nowym kontenerze i powiązanym z nim wolumenie
- Wyłączam kontener z GitLab
- Przywracam dane z kopii zapasowej do nowej bazy
- Uruchamiam ponownie kontener z GitLab
Detale migracji
Cały proces migracji rozpoczynamy od wyłączenia wszystkich komponentów naszej instalacji. Ja do zarządzania kontenerami w tym przypadku używam docker-compose, więc zmiany w konfiguracji polegają na edycji pliku konfiguracyjnego stosu.
W pierwszym kroku tworzymy nowy kontener z bazą danych i przypisujemy mu nowy wolumen na dane. W mojej instalacji baza danych uruchamiana była w kontenerze o nazwie postgresql
z podłączonym wolumenem postgresql
. Nowa baza i połączony z nią wolumen noszą nazwę pgsql
. Wszystko, co muszę zrobić, to skopiować całą sekcję konfiguracji kontenera i wolumenu postgresql
i zmienić nazwę. Dodatkowo w sekcji image
muszę podać etykietę nowej wersji bazy. Oczywiście i w tej bazie muszę udostępnić na zewnątrz port 5432
, aby podłączyć się do bazy za pomocą PgAdmin
Po uruchomieniu tak przygotowanego stosu GitLab pomyśli, że ma do czynienia z nową instalacją. Uruchomione zostaną zatem mechanizmy (cookbooki w Chef), które zainicjują bazę, w tym przede wszystkim stworzą odpowiedniego użytkownika i role. Jeżeli spróbujemy odtworzyć z kopii zapasowej dane bez wcześniejszego utworzenia roli, to zobaczymy na ekranie masę informacji o błędach. Ręczne przeniesienie roli moim zdaniem jest zadaniem nietrywialnym, czasochłonnym i wymaga dość dobrej znajomości budowy i obsługi bazy PostgreSQL. Dlatego wolę by GitLab zainicjował te dane od początku. Gdy to operacja ta zostanie wykonana, wyłączamy sam kontener z GitLab-em i odtwarzamy dane. Pamiętajmy, aby odtworzyć tylko bazę gitlabhq_production
.
Jeżeli nie zobaczyliśmy żadnych błędów związanych z przywracaniem kopii zapasowej, możemy ponownie uruchomić kontener z GitLab. Warto obserwować logi na konsoli, czy w trakcie tego procesu nie są zgłaszane błędu. U mnie wszystko udało się bezproblemowo i po chwili mogłem zalogować się ponownie do GitLab, ale już z nową wersją bazy.
Podsumowanie
Aktualizacja kontenera bazy danych została wykonana 2 dni temu i na razie nie zauważyłem utraty danych w trakcie migracji ani żadnych nieprawidłowości w działaniu GitLab-a. Dlatego uważam migrację za zakończoną sukcesem. Ale na wszelki wypadek nie usuwam jeszcze starego wolumenu ani kopii zapasowej.
Zaprezentowana metoda, jak już wspomniałem, nie jest opisana w oficjalnej dokumentacji, dlatego jeżeli chcesz ją stosować u siebie, to najpierw wykonaj testy w odizolowanym środowisku.
Plik konfiguracyjny stosu z GitLab-CE zamieszczam na oficjalnym repozytorium Szkoły DevNet. Możesz go pobrać stąd.