Como atualizar o container do acoplador após a alteração da sua imagem

Digamos que puxei a imagem oficial do mysql: 5.6.21.

Implantei esta imagem criando vários contentores de ancoragem.

estes contentores estão a funcionar há algum tempo até que o MySQL 5.6.22 seja libertado. A imagem oficial do mysql: 5.6 é atualizada com o novo lançamento, mas meus contêineres ainda funcionam 5.6.21.

Como propagar as alterações na imagem (isto é, actualizar a MySQL distro) para todos os meus recipientes existentes? Qual é a maneira correcta de atracar? de fazer isto?

 360
Author: zkilnbqi, 2014-11-04

13 answers

Depois de avaliar as respostas e estudar o tema, gostaria de resumir.

A forma de actualizar os contentores parece ser a seguinte:

Os recipientes de aplicação não devem conservar os dados da aplicação. Desta forma, poderá substituir o contentor de aplicações pela sua versão mais recente a qualquer momento, executando algo do género:

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

Pode guardar os dados na máquina(na pasta montada como volume) ou no (s) recipiente (S) Especial (s) apenas para dados. Continuar sobre isso aqui, Aqui , e Aqui.

Actualizar as aplicações (p.ex. com yum / apt-get upgrade) dentro dos recipientes é considerado um anti-padrão . Os recipientes de aplicação devem ser imutáveis, o que deve garantir um comportamento reprodutível. Algumas imagens oficiais da aplicação (mysql:5.6 em particular) nem sequer são projetadas para auto-atualização (apt-get upgrade não vai funcionar).

Gostaria de agradecer a todos os que deram as suas respostas, por isso ... podíamos ver abordagens diferentes.
 418
Author: Yaroslav Stavnichiy, 2017-05-23 11:33:24
Não gosto de montar volumes como uma ligação a uma lista de servidores, por isso, inventei um padrão para actualizar contentores de docker com contentores totalmente geridos pela docker. A criação de um novo container docker com --volumes-from <container> dará ao novo container com as imagens atualizadas propriedade compartilhada dos volumes gerenciados pelo docker.
docker pull mysql
docker create --volumes-from my_mysql_container [...] --name my_mysql_container_tmp mysql

Ao NÃO remover imediatamente o my_mysql_container original ainda, você tem a capacidade de voltar para o recipiente de trabalho conhecido se o recipiente melhorado não tem o dados certos,ou falha num teste de sanidade.

Neste momento, costumo fazer os guiões de reserva que tenho para o contentor dar uma rede de segurança para o caso de algo correr mal.
docker stop my_mysql_container
docker start my_mysql_container_tmp
Agora você tem a oportunidade de se certificar de que os dados que você espera estar no novo recipiente estão lá e fazer uma verificação de sanidade.
docker rm my_mysql_container
docker rename my_mysql_container_tmp my_mysql_container

Os volumes do acoplador ficarão por aqui enquanto qualquer contentor os estiver a usar, para que possa apagar o contentor original em segurança. Uma vez o recipiente original é removido, o novo recipiente pode assumir o nome do original para fazer tudo tão bonito como era para começar.

Existem duas grandes vantagens em utilizar este padrão para actualizar os contentores do Cais. Em primeiro lugar, elimina a necessidade de montar volumes para hospedar diretórios, permitindo que os volumes sejam diretamente transferidos para um recipiente atualizado. Em segundo lugar, você nunca está em uma posição onde não há um container docker de trabalho; assim, se a atualização falhar, você pode facilmente reverter para como estava a funcionar antes, girando novamente o contentor original do ancoradouro.
 59
Author: kMaiSmith, 2015-11-05 03:56:18

Gostaria de acrescentar que, se quiser fazer este processo automaticamente (transferir, parar e reiniciar um novo contentor com as mesmas configurações descritas por @Yaroslav), poderá usar a Torre de Vigilância. Um programa que actualiza automaticamente os seus contentores quando são alterados https://github.com/v2tec/watchtower

 18
Author: Ricardo Polo, 2017-07-06 10:21:35

Considere para estas respostas:

  • o nome da base de dados é app_schema
  • o nome do contentor é app_db
  • a senha de root é:root123

Como actualizar o MySQL ao armazenar os dados da aplicação dentro do recipiente

Isto é considerado uma má prática, Porque se você perder o recipiente, você perderá os dados. Embora seja uma má prática, aqui está uma maneira possível de fazê-lo:

1) Faça uma pesquisa de base de dados como SQL:

docker exec app_db sh -c 'exec mysqldump app_schema -uroot -proot123' > database_dump.sql

2) Actualizar a imagem:

docker pull mysql:5.6

3) Actualizar o contentor:

docker rm -f app_db
docker run --name app_db --restart unless-stopped \
-e MYSQL_ROOT_PASSWORD=root123 \
-d mysql:5.6

4) repor o resultado da base de Dados:

docker exec app_db sh -c 'exec mysql -uroot -proot123' < database_dump.sql

Como actualizar o contentor MySQL usando um volume externo

Usar um volume externo é uma forma melhor de gerir os dados, e torna mais fácil actualizar o MySQL. Perder o recipiente não vai perder nenhum dado. Você pode usar docker-compose para facilitar a gestão de aplicações de Docker multi-container numa única máquina:

1) Crie o ficheiro docker-compose.yml para gerir as suas aplicações:

version: '2'
services:
  app_db:
    image: mysql:5.6
    restart: unless-stopped
    volumes_from: app_db_data
  app_db_data:
    volumes: /my/data/dir:/var/lib/mysql

2) Actualizar o MySQL (da mesma pasta que o ficheiro docker-compose.yml):

docker-compose pull
docker-compose up -d
Nota: o último comando acima irá actualizar a imagem MySQL, recriar e iniciar o contentor com a nova imagem.
 15
Author: Alexandre Verri, 2017-01-15 04:35:30

Resposta semelhante à acima

docker images | awk '{print $1}' | grep -v 'none' | grep -iv 'repo' | xargs -n1 docker pull
 11
Author: Eddie Jaoude, 2016-10-08 03:46:54
Apenas para fornecer uma resposta mais geral (não específica de mysql)...
  1. em resumo

Sincronizar com o registo de imagens de Serviço ( https://docs.docker.com/compose/compose-file/#image):

docker-compose pull 

Recriar o contentor se o ficheiro de composição do 'docker' ou a imagem tiverem mudado:

docker-compose up -d
  1. antecedentes

A gestão da imagem do contentor é uma das razões para usar a composição do 'docker' (ver https://docs.docker.com/compose/reference/up/)

Se houver contentores existentes para um serviço, e a configuração ou imagem do serviço tiver sido alterada após a criação do contentor, a docker-compose recolhe as alterações, parando e recriando os contentores (preservando volumes montados). Para evitar que a composição detecte alterações, use a bandeira --no-recriar.

Aspecto de gestão de dados também coberto pelo acoplador-composto através de montagem externa "volumes" (ver https://docs.docker.com/compose/compose-file/#volumes ) ou recipiente de dados.

Isto deixa intactas potenciais questões de compatibilidade retroativa e migração de dados, mas estas são questões "aplicativas", não específicas do acoplador, que têm de ser verificadas com notas de lançamento e testes...

 10
Author: Ronan Fauglas, 2017-04-20 09:45:33

Aqui está o que parece usar {[[0] } ao construir um personalizado Dockerfile.

  1. crie primeiro o seu ficheiro de Dockerfile personalizado, adicionando um número de versão seguinte para diferenciar. Ex: docker build -t imagename:version . Isto irá armazenar a sua nova versão localmente.
  2. corre docker-compose down
  3. edite o seu ficheiro docker-compose.yml para reflectir o novo nome da imagem que definiu no Passo 1.
  4. corre docker-compose up -d Ele vai procurar localmente para a imagem e usar o seu atualizado.

- editar -

Os meus passos acima são mais verbos do que precisam de ser. Optimizei o meu fluxo de trabalho, incluindo o parâmetro build: . no meu ficheiro de composição de docker. Os passos parecem agora:

    Verifique se o meu ficheiro Dockerfile é o que eu quero que pareça.
  1. Defina o número de versão do meu nome de imagem no meu ficheiro de composição do 'docker'.
  2. Se a minha imagem ainda não foi construída: executar docker-compose build
  3. corre docker-compose up -d
Na altura, não me apercebi, mas a composição do ancoradouro é inteligente o suficiente para actualizar o meu contentor para o nova imagem com o comando um, em vez de ter que derrubá-la primeiro.
 7
Author: gdbj, 2018-03-02 18:26:09

A partir de http://blog.stefanxo.com/2014/08/update-all-docker-images-at-once/

Pode actualizar todas as suas imagens existentes usando o seguinte 'pipeline' de comandos:

docker images | awk '/^REPOSITORY|\<none\>/ {next} {print $1}' | xargs -n 1 docker pull
 4
Author: gvlx, 2015-08-31 11:45:21

Você precisa reconstruir todas as imagens e reiniciar todos os recipientes, ou de alguma forma atualizar o software e reiniciar o banco de dados. Não há nenhum caminho de atualização, mas que você projetar a si mesmo.

 3
Author: seanmcl, 2014-11-04 12:58:43

Se não quiser usar a composição do 'Docker', posso recomendar portainer . Tem uma função recriar que lhe permite recriar uma imagem enquanto puxa a imagem mais recente.

 2
Author: beruic, 2018-01-04 20:23:17

Certifique-se de que está a usar volumes para todos os dados persistentes (configuração, registos ou dados da aplicação) que armazena nos contentores relacionados com o estado dos processos dentro desse contentor. Actualize o seu ficheiro de Dockerfile e reconstrua a imagem com as alterações que deseja, e reinicie os contentores com os seus volumes montados no local apropriado.

 1
Author: Daniel Dinnyes, 2016-05-25 14:48:49
Isto é algo com que também tenho lutado pelas minhas próprias imagens. Tenho um ambiente de servidor a partir do qual crio uma imagem do acoplador. Quando eu atualizar o servidor, eu gostaria que todos os usuários que estão executando containers com base na minha imagem Docker para ser capaz de atualizar para o servidor mais recente.

Idealmente, eu preferiria gerar uma nova versão da imagem Docker e ter todos os recipientes baseados em uma versão anterior dessa imagem automaticamente atualizada para a nova imagem "no lugar."Mas isto o mecanismo não parece existir.

Então o próximo melhor design que eu fui capaz de criar até agora é fornecer uma maneira de ter o container atualizado-similar a como um aplicativo desktop verifica para atualizações e depois atualiza-se a si mesmo. No meu caso, isto provavelmente significará criar um script que envolve git puxa de uma etiqueta bem conhecida.

A imagem / contentor não muda, mas os" internos " do contentor mudam. Você poderia imaginar fazer o mesmo com apt-get, yum, ou o que for apropriado para o seu ambiente. Junto com isso, eu atualizaria o myserver:a última imagem no registro para que quaisquer novos contêineres fossem baseados na última imagem.

Estaria interessado em saber se há alguma arte anterior que aborde este cenário.
 1
Author: bjlevine, 2017-03-03 13:48:31