Docker-Compose persistente Daten MySQL

156

Ich kann nicht scheinen, dass MySQL-Daten bestehen bleiben, wenn ich $ docker-compose downFolgendes ausführe.yml

version: '2'
services:
  # other services

  data:
    container_name: flask_data
    image: mysql:latest
    volumes:
      - /var/lib/mysql
    command: "true"

  mysql:
    container_name: flask_mysql
    restart: always
    image: mysql:latest
    environment:
      MYSQL_ROOT_PASSWORD: 'test_pass' # TODO: Change this
      MYSQL_USER: 'test'
      MYSQL_PASS: 'pass'
    volumes_from:
      - data
    ports:
      - "3306:3306"

Ich verstehe, dass in meinem dataContainer mithilfe volumes: - /var/lib/mysqlvon Zuordnungen die Zuordnung zu meinem lokalen Maschinenverzeichnis erfolgt, in dem MySQL Daten im Container speichert. Aufgrund dieser Zuordnung sollten die Daten auch dann bestehen bleiben, wenn die Container zerstört werden. Und der mysqlContainer ist nur eine Client-Schnittstelle in die Datenbank und kann das lokale Verzeichnis wegen sehenvolumes_from: - data

Ich habe diese Antwort versucht und es hat nicht funktioniert. Docker-Compose Persistent Data Trouble

BEARBEITEN

Ich habe mein .ymlwie unten gezeigt geändert und ein Verzeichnis erstellt, ./dataaber jetzt, wenn ich docker-compose up --buildden mysqlContainer starte, wird kein Fehler ausgelöst

  data:
    container_name: flask_data
    image: mysql:latest
    volumes:
      - ./data:/var/lib/mysql
    command: "true"

  mysql:
    container_name: flask_mysql
    restart: always
    image: mysql:latest
    environment:
      MYSQL_ROOT_PASSWORD: 'test_pass' # TODO: Change this
      MYSQL_USER: 'test'
      MYSQL_PASS: 'pass'
    volumes_from:
      - data
    ports:
      - "3306:3306"


flask_mysql | mysqld: Can't create/write to file '/var/lib/mysql/is_writable' (Errcode: 13 - Permission denied)
flask_mysql | 2016-08-26T22:29:21.182144Z 0 [Warning] TIMESTAMP with implicit DEFAULT value is deprecated. Please use --explicit_defaults_for_timestamp server option (see documentation for more details).
flask_mysql | 2016-08-26T22:29:21.185392Z 0 [ERROR] --initialize specified but the data directory exists and is not writable. Aborting.
Adam
quelle

Antworten:

220

Der Datencontainer ist eine überflüssige Problemumgehung. Datenmengen würden den Trick für Sie tun. Ändern Sie Ihre docker-compose.ymlzu:

version: '2'
services:
  mysql:
    container_name: flask_mysql
    restart: always
    image: mysql:latest
    environment:
      MYSQL_ROOT_PASSWORD: 'test_pass' # TODO: Change this
      MYSQL_USER: 'test'
      MYSQL_PASS: 'pass'
    volumes:
      - my-datavolume:/var/lib/mysql
volumes:
  my-datavolume:

Docker erstellt das Volume für Sie im /var/lib/docker/volumesOrdner. Diese Lautstärke bleibt bestehen, solange Sie nicht tippendocker-compose down -v

Oh man
quelle
18
Ab MySQL 5.7.6 treten (erneut) Berechtigungsprobleme mit dem mysqlDocker-Image auf. Sie können stattdessen das mariadbDocker-Image verwenden, das mit Docker-Volumes einwandfrei funktioniert .
Peterino
Diese Lösung hat bei mir funktioniert. Einige Randnotizen / Präzisionen: 1. Wenn Sie die obige Konfiguration in docker-compose.yml verwenden und Ihren Service-Stack mit "docker stack deploy -c docker-compose.yml mystack" bereitstellen, müssen Sie das nicht erstellen Volume manuell, es wird automatisch für Sie als / var / lib / docker / volume / mystack_my-datavolume erstellt (beachten Sie, dass dem Volume-Namen "mystack_" vorangestellt wird). 2. Ich musste die Berechtigungen für mein Verzeichnis nicht ändern. Selbst wenn ich Dateien in meinem Container habe, die mysql: root gehören, wurden sie ohne Probleme als 27: root auf meinem Docker-Host erstellt.
Joey Cote
10
Warum möchten Sie es jemals speichern, var/lib/docker/volumesanstatt ein Verzeichnis in Ihrem Projektordner zu haben data/mysql?
Der Pate
@TheGodfather Meine Vermutung wäre, wenn Sie MySQL-Daten nicht auf Ihrer Produktionsmaschine bereitstellen möchten. Ansonsten ist das eine sehr gute Idee, alles zusammenzuhalten.
Duncan
1
@louhow Ich denke, weil ich mich sicherer fühle, wenn alle Teile meiner App und Daten irgendwie zusammen gespeichert sind, und ich keine Abhängigkeiten von einem bestimmten Volumen von irgendwoher habe
The Godfather
53

Es gibt drei Möglichkeiten:

Erster Weg

Sie müssen das Verzeichnis angeben, in dem MySQL-Daten auf Ihrem Host-Computer gespeichert werden sollen . Sie können dann den Datencontainer entfernen. Ihre MySQL-Daten werden in Ihrem lokalen Dateisystem gespeichert.

Die Definition des MySQL-Containers muss folgendermaßen aussehen:

mysql:
  container_name: flask_mysql
  restart: always
  image: mysql:latest
  environment:
    MYSQL_ROOT_PASSWORD: 'test_pass' # TODO: Change this
    MYSQL_USER: 'test'
    MYSQL_PASS: 'pass'
volumes:
 - /opt/mysql_data:/var/lib/mysql
ports:
  - "3306:3306"

Zweiter Weg

Wäre, den Datencontainer vor der Eingabe festzuschreiben docker-compose down:

docker commit my_data_container
docker-compose down

Dritter Weg

Sie können auch docker-compose stopanstelle von verwenden docker-compose down(dann müssen Sie den Container nicht festschreiben)

Bucharow Sergey
quelle
Kann ich nicht einfach haben, volumes: - /var/lib/mysqlweil es zugeordnet ist HOST:CONTAINERund wenn Sie keinen Doppelpunkt angeben, wird dasselbe Verzeichnis zugeordnet?
Adam
Nicht. Leider in diesem Fall ordnen Docker dieses Container-Verzeichnis einem zufälligen Host-Ordner wie/var/lib/docker/volumes/ec3c543bc92f114c2c568733541e89381881e5a62996d7084e07793f86280535
Bukharov Sergey
Okay, ich dachte, volumes: - /var/lib/mysqles wäre gleichbedeutend mitvolumes: - /var/lib/mysql:/var/lib/mysql
Adam
Ihr dritter Weg wird nicht funktionieren, da Docker keine Daten von Volumes in das Image festschreibt. siehe github.com/moby/moby/issues/6999
Ohmen
13

Sie müssen ein separates Volume für MySQL-Daten erstellen.

So wird es aussehen:

volumes_from:
  - data
volumes:
  - ./mysql-data:/var/lib/mysql

Und nein, /var/lib/mysqlist ein Pfad in Ihrem MySQL-Container und hat nichts mit einem Pfad auf Ihrem Host-Computer zu tun. Ihr Host-Computer verfügt möglicherweise überhaupt nicht über MySQL. Das Ziel ist es also, einen internen Ordner aus einem MySQL-Container beizubehalten.

Dmitry Malyshenko
quelle
Wäre dies nicht nicht anders sein als mein Wechsel volumesunter den Datencontainer zu dem, was Sie unter Ihrem setzen volumesund einfach hatte volumes_from: - datafür mysql? Auch versucht dies und thew einen neuen Fehler. Sagt, dass dir existiert, aber nicht beschreibbar ist und der mysqlContainer nicht ausgeführt wird.
Adam
Natürlich müssen Sie einen lokalen Ordner mit einem Pfad ./mysql-data (oder was auch immer Sie vor dem Semikolon setzen würden)
erstellen
Siehe meine Bearbeitung. Ich habe es nicht verstanden, bevor du es kommentiert hast. Aber habe lokales Verzeichnis erstellt. Anscheinend gibt es jetzt ein Berechtigungsproblem.
Adam
FEHLER: Der Dienst "mysql" stellt Volumes aus "Daten" bereit, die nicht der Name eines Dienstes oder Containers sind.
Massimiliano Arione
10

Eigentlich ist dies der Pfad und Sie sollten einen gültigen Pfad angeben, damit dies funktioniert. Wenn sich Ihr Datenverzeichnis im aktuellen Verzeichnis befindet my-data, sollten Sie es stattdessen erwähnen ./my-data, andernfalls wird Ihnen dieser Fehler in mysqlund mariadbauch angezeigt .

volumes:
 ./my-data:/var/lib/mysql
Codelearner
quelle