Po przeanalizowaniu odpowiedzi i przestudiowaniu tematu chciałbym podsumować.
Wygląda na to, że Docker uaktualnia kontenery:
Kontenery aplikacji nie powinny przechowywać danych aplikacji . W ten sposób możesz w dowolnym momencie zastąpić kontener aplikacji nowszą wersją, wykonując coś takiego:
docker pull mysql
docker stop my-mysql-container
docker rm my-mysql-container
docker run --name=my-mysql-container --restart=always \
-e MYSQL_ROOT_PASSWORD=mypwd -v /my/data/dir:/var/lib/mysql -d mysql
Możesz przechowywać dane na hoście (w katalogu zamontowanym jako wolumin) lub w specjalnych kontenerach tylko z danymi . Przeczytaj więcej na ten temat
Aktualizowanie aplikacji (np. Z aktualizacją yum / apt-get) w kontenerach jest uważane za anty-wzorzec . Pojemniki z aplikacjami powinny być niezmienne , co gwarantuje powtarzalne zachowanie. Niektóre oficjalne obrazy aplikacji (w szczególności mysql: 5.6) nie są nawet zaprojektowane do samodzielnej aktualizacji (aktualizacja apt-get nie będzie działać).
Chciałbym podziękować wszystkim, którzy udzielili odpowiedzi, abyśmy mogli zobaczyć różne podejścia.
Jarosław Stawnichij
źródło
docker rename my-mysql-container trash-container
przed utworzeniem nowego?Nie lubię montować woluminów jako łącza do katalogu hosta, więc wymyśliłem wzorzec uaktualniania kontenerów dokowanych z kontenerami zarządzanymi całkowicie przez dokerów. Utworzenie nowego kontenera dokowanego za pomocą
--volumes-from <container>
spowoduje, że nowy kontener ze zaktualizowanymi obrazami będzie współwłasnością woluminów zarządzanych przez dokera.Nie usuwając
my_mysql_container
jeszcze oryginału , możesz wrócić do znanego działającego kontenera, jeśli zmodernizowany kontener nie ma odpowiednich danych lub nie przejdzie testu zdrowego rozsądku.W tym momencie zwykle uruchamiam wszystkie skrypty tworzenia kopii zapasowych, które mam dla kontenera, aby zapewnić sobie siatkę bezpieczeństwa na wypadek, gdyby coś poszło nie tak
Teraz masz możliwość upewnienia się, że dane, które mają znajdować się w nowym kontenerze, znajdują się na miejscu i przeprowadzenia kontroli poczytalności.
Woluminy dokowania będą się trzymać tak długo, jak długo będzie z nich korzystać dowolny pojemnik, dzięki czemu można bezpiecznie usunąć oryginalny pojemnik. Po usunięciu oryginalnego pojemnika nowy pojemnik może przyjąć nazwę oryginału, aby wszystko było tak ładne, jak miało się rozpocząć.
Istnieją dwie główne zalety używania tego wzorca do aktualizacji kontenerów dokerów. Po pierwsze, eliminuje potrzebę montowania woluminów w katalogach hosta, umożliwiając bezpośrednie przenoszenie woluminów do zmodernizowanych kontenerów. Po drugie, nigdy nie jesteś w pozycji, w której nie ma działającego kontenera dokowanego; więc jeśli aktualizacja się nie powiedzie, możesz łatwo powrócić do poprzedniego stanu, ponownie rozpinając oryginalny pojemnik dokowania.
źródło
./postgres-data/:/var/lib/postgres/data
./postgres-data/
Tylko dla zapewnienia bardziej ogólnej (nie specyficznej dla MySQL) odpowiedzi ...
Synchronizuj z rejestrem obrazu usługi ( https://docs.docker.com/compose/compose-file/#image ):
Odtwórz kontener, jeśli plik lub obraz skomponowany przez dokera zmienił się:
Zarządzanie obrazami kontenerów jest jednym z powodów używania docker-compose (patrz https://docs.docker.com/compose/reference/up/ )
Aspekt zarządzania danymi jest również objęty komponentem dokującym poprzez zamontowane zewnętrzne „woluminy” (patrz https://docs.docker.com/compose/compose-file/#volumes ) lub kontener danych.
Pozostawia to potencjalne problemy z kompatybilnością wsteczną i migracją danych, ale są to problemy „aplikacyjne”, a nie specyficzne dla Dockera, które należy sprawdzić w informacjach o wersji i testach ...
źródło
Chciałbym dodać, że jeśli chcesz wykonać ten proces automatycznie (pobierz, zatrzymaj i zrestartuj nowy pojemnik z tymi samymi ustawieniami, jak opisane przez @Yaroslav), możesz użyć Strażnicy. Program, który automatycznie aktualizuje pojemniki po ich zmianie https://github.com/v2tec/watchtower
źródło
Rozważ te odpowiedzi:
app_schema
app_db
root123
Jak zaktualizować MySQL podczas przechowywania danych aplikacji w kontenerze
Jest to uważane za złą praktykę , ponieważ jeśli stracisz pojemnik, stracisz dane. Chociaż jest to zła praktyka, oto możliwy sposób, aby to zrobić:
1) Wykonaj zrzut bazy danych jako SQL:
2) Zaktualizuj obraz:
3) Zaktualizuj kontener:
4) Przywróć zrzut bazy danych:
Jak zaktualizować kontener MySQL przy użyciu zewnętrznego woluminu
Korzystanie z zewnętrznego woluminu jest lepszym sposobem zarządzania danymi i ułatwia aktualizację MySQL. Utrata pojemnika nie spowoduje utraty żadnych danych. Możesz użyć komponowania dokującego, aby ułatwić zarządzanie aplikacjami dokującymi z wieloma kontenerami na jednym hoście:
1) Utwórz
docker-compose.yml
plik, aby zarządzać aplikacjami:2) Zaktualizuj MySQL (z tego samego folderu co
docker-compose.yml
plik):Uwaga: ostatnie polecenie powyżej zaktualizuje obraz MySQL, odtworzy i uruchom kontener z nowym obrazem.
źródło
docker-compose
, czy to zadziała? stackoverflow.com/a/31485685/65313volumes_from
Klucz jest teraz przestarzały (nawet usunięty w wersji 3 pliku tworzenia) na korzyść nowegovolumes
klucza.docker pull image_uri:tag && docker restart container_running_that_image
pracował dla mnie. Nie ma potrzebydocker-compose pull && docker-compose up -d
.Podobna odpowiedź do powyższej
źródło
Oto, jak to wygląda przy
docker-compose
tworzeniu niestandardowegoDockerfile
.docker build -t imagename:version .
lokalnie zapisze nową wersję.docker-compose down
docker-compose.yml
plik, aby odzwierciedlić nową nazwę obrazu ustawioną w kroku 1.docker-compose up -d
. Lokalnie wyszuka obraz i użyje zaktualizowanego.-EDYTOWAĆ-
Moje kroki powyżej są bardziej szczegółowe, niż powinny. Zoptymalizowałem przepływ pracy, włączając
build: .
parametr do mojego pliku dokowania. Kroki wyglądają teraz tak:docker-compose build
docker-compose up -d
Nie zdawałem sobie wtedy sprawy, ale kompilacja dokerów jest wystarczająco inteligentna, aby po prostu zaktualizować mój kontener do nowego obrazu za pomocą jednego polecenia, zamiast najpierw go obniżać.
źródło
docker-compose up -d
bez konieczności zatrzymywania wszystkiego w pierwszej kolejności.Jeśli nie chcesz używać Docker Compose, mogę polecić portainer . Ma funkcję odtwarzania, która pozwala odtworzyć kontener podczas pobierania najnowszego obrazu.
źródło
Musisz albo odbudować wszystkie obrazy i zrestartować wszystkie kontenery, albo jakoś zaktualizować oprogramowanie i zrestartować bazę danych. Nie ma ścieżki uaktualnienia, ale którą sam zaprojektujesz.
źródło
docker restart
polecenie, ale nie jestem pewien, czy wykryje zmiany obrazu. A co dzieje się z moimi danymi w kontenerach?Biorąc z http://blog.stefanxo.com/2014/08/update-all-docker-images-at-once/
Możesz zaktualizować wszystkie istniejące obrazy za pomocą następującego potoku poleceń:
źródło
Upewnij się, że używasz woluminów dla wszystkich trwałych danych (konfiguracji, dzienników lub danych aplikacji), które przechowujesz w kontenerach związanych ze stanem procesów w tym kontenerze. Zaktualizuj plik Docker i odbuduj obraz z żądanymi zmianami, a następnie ponownie uruchom kontenery z woluminami zamontowanymi w odpowiednim miejscu.
źródło
Z tym też walczyłem o własne zdjęcia. Mam środowisko serwerowe, z którego tworzę obraz Docker. Gdy aktualizuję serwer, chciałbym, aby wszyscy użytkownicy, którzy używają kontenerów opartych na moim obrazie Docker, mogli uaktualnić do najnowszego serwera.
Idealnie wolałbym wygenerować nową wersję obrazu Docker i wszystkie kontenery oparte na poprzedniej wersji tego obrazu aktualizowały się automatycznie do nowego obrazu „na swoim miejscu”. Ale ten mechanizm wydaje się nie istnieć.
Kolejnym najlepszym projektem, jaki udało mi się do tej pory wymyślić, jest zapewnienie sposobu, aby sama aktualizacja kontenera była podobna do tego, w jaki sposób aplikacja komputerowa sprawdza dostępność aktualizacji, a następnie sama się aktualizuje. W moim przypadku prawdopodobnie będzie to oznaczać wykonanie skryptu, który będzie pobierał Git ze znanego tagu.
Obraz / kontener tak naprawdę się nie zmienia, ale zmieniają się „elementy wewnętrzne” tego kontenera. Możesz sobie wyobrazić, że robisz to samo z apt-get, yum lub czymkolwiek odpowiednim dla twojego środowiska. Wraz z tym zaktualizowałbym mój serwer: najnowszy obraz w rejestrze, aby wszelkie nowe kontenery były oparte na najnowszym obrazie.
Chciałbym dowiedzieć się, czy istnieje jakikolwiek stan techniki, który dotyczy tego scenariusza.
źródło
Aktualizacja
Służy to głównie zapytaniu o kontener, aby nie aktualizować, ponieważ sposobem jest budowanie obrazów
Miałem ten sam problem, więc utworzyłem okno dokowane , bardzo proste narzędzie wiersza polecenia, które działa wewnątrz kontenera dokowanego w celu aktualizacji pakietów w innych działających kontenerach.
Używa docker-py do komunikowania się z uruchomionymi kontenerami dokerów i aktualizacji pakietów lub uruchamiania dowolnych pojedynczych poleceń
Przykłady:
docker run --rm -v /var/run/docker.sock:/tmp/docker.sock itech/docker-run exec
domyślnie uruchomi to
date
polecenie we wszystkich działających kontenerach i zwróci wyniki, ale możesz wydać dowolne polecenie npdocker-run exec "uname -a"
Aby zaktualizować pakiety (aktualnie tylko przy użyciu apt-get):
docker run --rm -v /var/run/docker.sock:/tmp/docker.sock itech/docker-run update
Możesz tworzyć i alias i używać go jako zwykłej linii poleceń, np
alias docker-run='docker run --rm -v /var/run/docker.sock:/tmp/docker.sock itech/docker-run'
źródło
apt update; apt upgrade
, obraz wzrośnie.)