Journal Sauvegarder le contenu d’un container Docker avec BackupPC

Posté par  (site web personnel) . Licence CC By‑SA.
Étiquettes : aucune
10
9
nov.
2021

Sommaire

Dans un environnement de production il est important de réaliser des sauvegardes (en mode dev aussi d’ailleurs). Docker nous apporte une très grande souplesse et facilement nous pouvons proposer différents services. Mais comment faire pour sauvegarder le contenu de ces services ? Pour illustrer cette exemple, j’utiliserais Glpi.

Je part du principe que vous maîtrisez BackupPC, Docker, Docker-compose, Glpi et Traefik. Chaque brique est opérationnel et je détaillerais uniquement ce qui est en lien avec le script.

Pourquoi le contenu ?

Nos containers mènent leurs petites vies, dans notre exemple Glpi est utilisé pour maintenir l’inventaire du parc informatique (matériel et financier) avec le plugin Fusion Inventory et aussi pour gérer les tickets du support. Vous vous imaginez bien que toutes ces données changent en permanence et qu’il est important de pouvoir les restaurer en cas de crash.

Par défaut Docker propose une solution basique pour « sauvegarder » un container : docker export. Au préalable cela demande de faire un commit et espérer qu’aucun enregistrement sera fait dans la base de données lorsque vous exécuterez l’export. Donc autant dire que c’est peine perdu et de plus un container seul ne sert quasiment à rien sans son Dockerfile ou docker-compose.yml (voir les deux). Autre problème : la volumétrie. A chaque export c’est l’intégralité du container que vous copiez dans un fichier « tar » et il devient difficile de l’intégrer dans le système de déduplication de BackupPC.

La genèse

Pour notre exemple nous utiliserons deux serveurs :

  • svbackup : serveur de sauvegarde où sera installé et paramétré BackupPC;
  • svdocker : serveur docker où sera installé docker, docker-compose, Traefik, mysqldump, rsync.

La communication entre ces serveurs ce fera par ssh avec échange de clés pour ne plus avoir besoin de saisir les mots de passe.

Au début il y avait docker-compose

Pour construire mes container j’utilise docker-compose. Dans BackupPC je créé un job qui sera chargé de copier uniquement les fichiers de configurations et créations de mes containers. Sur svdocker nous les stockerons dans le dossier /home de l’utilisateur backuppc.

Naquirent les containers

Pour Glpi j’utilise deux containers, un premier pour la partie web et un autre pour la partie mysql.

docker-compose.yml

version: '3.3'
services:
  glpi_mysql:
    image: mysql:latest
    container_name: glpi_mysql
    hostname: glpi_mysql
    command: --default-authentication-plugin=mysql_native_password
    env_file:
      - ./mysql.env
    volumes:
      - "/var/lib/mysql/glpi:/var/lib/mysql"
    networks:
      - traefik
    restart: always

  # use a Dockerfile
  glpi_www:
    depends_on:
      - glpi_mysql
    build: .
    container_name: glpi_www
    volumes:
      - "/var/www/hml:/var/www/html"
    labels:
      - "traefik.enable=true"
      - "traefik.http.routers.glpi_www.rule=Host(`glpi.mondomaine.fr`)"
      - "traefik.http.routers.glpi_www.entrypoints=websecure"
      - "traefik.http.routers.glpi_www.tls.certresolver=le"
    networks:
      - traefik
    restart: always;

networks:
  traefik:
    external: true

Pour le container glpi_www j’utilise un Dockerfile qui se charge de télécharger l’image php:apache-7.3 et installer les dépendances nécessaires pour faire tourner Glpi. En l’état rien de bien exceptionnel. Vous pouvez voir que j’utilise Traefik pour accéder simplement au container glpi_www. En l’état tout devrait marcher.

Pour permettre à BackupPC de récupérer les informations nécessaire à la sauvegarde nous allons utiliser les labels.

docker-compose.yml

version: '3.3'
services:
  glpi_mysql:
    image: mysql:latest
    container_name: glpi_mysql
    hostname: glpi_mysql
    command: --default-authentication-plugin=mysql_native_password
    env_file:
      - ./mysql.env
    volumes:
      - "/var/lib/mysql/glpi:/var/lib/mysql"
    networks:
      - traefik
    restart: always

  # use a Dockerfile
  glpi_www:
    depends_on:
      - glpi_mysql
    build: .
    container_name: glpi_www
    volumes:
      - "/var/www/html:/var/www/html"
    labels:
      - "traefik.enable=true"
      - "traefik.http.routers.glpi_www.rule=Host(`glpi.mondomaine.fr`)"
      - "traefik.http.routers.glpi_www.entrypoints=websecure"
      - "traefik.http.routers.glpi_www.tls.certresolver=le"
      - "backuppc.active=true"
      - "backuppc.services=volume,"
      - "backuppc.volume.path=/var/www/html"
    networks:
      - traefik
    restart: always

networks:
  traefik:
    external: true

J’ai ajouté trois labels :

  • backuppc.active = true : active ou désactive la sauvegarde [true|false];
  • backuppc.services = volume, : type de services à sauvegarde. Pour le moment il est possible de sauvegarder les fichiers et la base de données Mysql. La virgule à la fin est obligatoire;
  • backuppc.volume.path = /var/www/html : répertoire dans le container à sauvegarder.

Télécharger le fichier backup-container.sh sur le serveur svdocker dans le dossier « home » de l’utilisateur backuppc. Sur le serveur svbackup connectez-vous à l’interface de BackupPC pour créer une machine nommé « docker-glpi_www ». Ce nom vous permettra de retrouver rapidement votre sauvegarde dans la liste des machines enregistré. Il y a une subtilité car ce même nom est utilisé par BackupPC pour contrôler si la machine est accessible sur le réseau. Il va falloir contourner le problème en modifiant les champs ClientNameAlias, PingCmd en remplaçant la variable « $host » par le nom DNS de votre serveur Docker, ici : svdocker

dockerToBackuppc

Pour lancer la copie des fichiers du container vers l’hôte j’utilise la fonction « DumpPreUserCmd », pour faire simple cela permet de lancer un programme sur l’hôte avant que BackupPC rapatrie les fichiers. Ici nous allons lancer le script backup-container.sh.

dockerToBackuppc

La commande :

$sshPath -x -l backuppc -i /home/backuppc/.ssh/id_rsa svdocker sudo /home/backuppc/./backup-container.sh -d glpi_www

Explication :

  • $sshPath -x -l backuppc -i /home/backuppc/.ssh/id_rsa svdocker : se connecte en ssh à svdocker avec l’utilisateur backuppc et la clé associée;
  • sudo /home/backuppc/./backup-container.sh -d glpi_www : lance le script backup-container.sh avec en paramètre le nom du container à sauvegarder. Par défaut les fichiers du container sont copiés dans le dossier /export/glpi_www de l’hôte donc il faut penser à indiquer à BackupPC où aller chercher les fichiers.

dockerToBackuppc

Il reste une dernière étape avant de lancer notre première sauvegarde. Le script copie les fichiers du container vers l’hôte dans le dossier /export/glpi_www, il est donc nécessaire de purger ce dossier après chaque sauvegarde. J’utilise cette fois l’option « DumpPostUserCmd »

dockerToBackuppc

Avec la commande

$sshPath -x -l backuppc -i /home/backuppc/.ssh/id_rsa svdocker sudo /home/backuppc/./backup-container.sh -d glpi_www -r

Le fonctionnement est le même que pour la commande de « predump ». A la différence que je passe le paramètre « -r » au script backup-container.sh pour effacer le contenu du dossier « /export/glpi_www ».

Vous pouvez enregistrer le jobs et faire vos premiers essais. Si tout ce passe bien vous pouvez suivre en live sur svdocker le répertoire « /export/glpi_www » se remplir, une fois fini BackupPC va les copier avec rsync et lancer la commande de purge du répertoire « /export/glpi_www ».

Et ma base ?

Avec Mysql l’idée est la même. Nous allons éditer le fichier docker-compose.yml de notre ensemble pour ajouter les labels nécessaire à mysql.

version: '3.3'
services:
  glpi_mysql:
    image: mysql:latest
    container_name: glpi_mysql
    hostname: glpi_mysql
    command: --default-authentication-plugin=mysql_native_password
    env_file:
      - ./mysql.env
    volumes:
      - "/var/lib/mysql/glpi:/var/lib/mysql"
    labels:
      - "traefik.enable=true"
      - "traefik.tcp.routers.glpi_mysql.rule=HostSNI(`*`)"
      - "traefik.tcp.services.glpi_mysql.loadBalancer.server.port=3306"
      - "traefik.tcp.routers.glpi_mysql.entrypoints=mysql"
      - "backuppc.active=true"
      - "backuppc.services=mysql,"
    networks:
      - traefik
    restart: always

[…]

Cette fois backuppc.services contient « mysql » comme valeur mais ce n’est pas plus important et délicat. Pour que cela marche correctement vous devez activer la connexion par TCP à Traefik de façon à pouvoir depuis l’hôte lancer mysqldump. Il aurait été possible de lancer mysqldump à l’intérieur du container mais cela imposait d'installer dans tout les container « mysqldump » avec toutes les dépendances.
Sur le serveur svbackup créer un job docker-glpi_mysql en reprenant les mêmes valeur que pour le précédent job à la différence des paramètres à passer au script backup_container :

$sshPath -x -l backuppc -i /home/backuppc/.ssh/id_rsa svdocker sudo /home/backuppc/./backup-container.sh -d glpi_mysql -u dbuser -p dbpassword -h glpi_mysql.mondomaine.fr -n glpi_prod -c

  • $sshPath -x -l backuppc -i /home/backuppc/.ssh/id_rsa svdocker : connexion à svdocker;
  • sudo /home/backuppc/./backup-container.sh -d glpi_mysql -u dbuser -p dbpassword -h glpi_mysql.mondomaine.fr -n glpi_prod -c : lance le script; -d : nom du container; -h : nom dns par lequel le container est joignable : dans notre exemple c’est « glpi_mysql.mondomaine.fr »; -n : nom de la base de données; -u : nom d’utilisateur mysql; -p : mot de passe mysql; -c : si ajouté compresse le fichier sql.

Il ne vous reste plus qu’à faire un test de sauvegarde.

Tout en un

Si votre container est à la fois le serveur web et le serveur mysql il va falloir modifier votre docker-compose.yml

version: '3.3' services:
  glpi:
    image: mysql:latest
    container_name: glpi
    hostname: glpi
    command: --default-authentication-plugin=mysql_native_password
    env_file:
      - ./mysql.env
    volumes:
      - "/var/lib/mysql/glpi:/var/lib/mysql"
      - "/var/www/html:/var/www/html"
    labels:
      - "traefik.enable=true"
      - "traefik.tcp.routers.glpi_mysql.rule=HostSNI(`*`)"
      - "traefik.tcp.services.glpi_mysql.loadBalancer.server.port=3306"
      - "traefik.tcp.routers.glpi_mysql.entrypoints=mysql"
      - "backuppc.active=true"
      - "backuppc.services=mysql,volume"
      - "backuppc.volume.path=/var/www/html"
    networks:
      - traefik
    restart: always

La commande de PreDump reste la même, il faut juste adapté le nom du container :

$sshPath -x -l backuppc -i /home/backuppc/.ssh/id_rsa svdocker sudo /home/backuppc/./backup-container.sh -d glpi -u dbuser -p dbpassword -c -n glpi_prod

  • # Dans le même genre

    Posté par  (site web personnel) . Évalué à 1.

    Très intéressant je ne connaissais pas backuppc, j'utilise l’excellentissime Bivac pour sauvegarder et deck-chores pour les commandes

  • # Commentaire supprimé

    Posté par  . Évalué à 3.

    Ce commentaire a été supprimé par l’équipe de modération.

  • # Quelque chose qui m'échappe

    Posté par  . Évalué à 7.

    Qu's-tu à sauvegarder exactement dans tes containers ?

    • [^] # Re: Quelque chose qui m'échappe

      Posté par  . Évalué à 6.

      Je m’apprêtais à écrire le même commentaire.

      Normalement, le contenu d'un container en lui même ne devrait pas changer. Les seules choses à sauvegarder devraient être dans des volumes.
      Et encore… pour mysql, on ne sauvegarde pas la base de données en copiant les fichiers, mais dans lui demandant de faire un export dans un autre volume dédié aux exports.

      Pour GLPi, a part peut être des fichiers de configuration… qui devraient être dans un volume, je suppose qu'il n'y a pas grand chose à sauvegarder. Ceci dit, on dirait que ça se configure via variable d'environnement. Donc a a moins d'aller chipoter dans les fichiers de GLPi pour bricoler, je vois pas trop non plus.

      • [^] # Commentaire supprimé

        Posté par  . Évalué à 2.

        Ce commentaire a été supprimé par l’équipe de modération.

        • [^] # Re: Quelque chose qui m'échappe

          Posté par  . Évalué à 6.

          Mais il existe des images mal fichues, où les données ne sont pas forcément dans un volume.

          Il est toujours possible de monter un volume dans un répertoire du container, même quand ça n'a pas été prévu via le Dockerfile.

          Là où c'est plus chiant à mettre en place, c'est quand les données sont dans le même répertoire que tout un tas de brol. Mais là encore, il y a souvent des solutions, comme monter un volume et créer des liens symboliques, ou encore inclure les dits fichiers dans un volume.

          • [^] # Commentaire supprimé

            Posté par  . Évalué à 1.

            Ce commentaire a été supprimé par l’équipe de modération.

        • [^] # Re: Quelque chose qui m'échappe

          Posté par  (Mastodon) . Évalué à 4.

          Cela permet de fournir une autre manière d'avoir des backups automatisés pour les SGBD, où sauvegarder directement les fichiers est une TRES mauvaise idée.

          Ça dépend de la granularité de récupération que tu veux avoir.

          Si tu veux pouvoir restaurer une db/une table ou quelques lignes effectivement c'est nul.

          Si tu veux juste du disaster recovery pour pallier à des gros crashes, c'est plus rapide de couper 5 secondes, faire un snap et relancer et faire un backup du snap.

          Tout dépend en fait si c'est une db partagée par des applis/clients multiples ou si c'est juste une db embarquée avec une appli métier.

          • [^] # Commentaire supprimé

            Posté par  . Évalué à 3.

            Ce commentaire a été supprimé par l’équipe de modération.

            • [^] # Re: Quelque chose qui m'échappe

              Posté par  (Mastodon) . Évalué à 3.

              Un backup, une fois fait, tu peux (et même doit) le tester. Ton snap, non, à moins de le remonter. Mais si tu le remontes, c'est que tu as un souci, et si tu as un souci lorsque tu le remontes, il est trop tard pour faire une sauvegarde.

              Qu'est-ce que tu entends par "le remonter"

              Pour tester une sauvegarde, on restore les données, quelque soit la manière de faire une sauvegarde. Et si la BD est stoppée, si c'est fiable.

              Et un admin compétent ne coupera jamais une BD 5s le temps de faire le backup alors qu'il existe nativement la possibilité de le faire sans.

              Tout dépend de l'utilisation. Pour une BD avec n accès concurrents à toute heure de la journée et pas de lien vers des données sur des fichiers "traditionnels" oui je suis d'accord.

              Pour une BD utilisée par une seule application, avec une foultitude de lien vers des fichiers attachés, stopper l'application et et faire un snapshot du volume où sont stocké les fichier est la meilleure manière d'avoir une cohérence entre BD et fichiers attaché. Si on fait ça quite à stopper l'appli on peut aussi décider de stopper la BD et la sauvegarder de la même façon si par exemple ça fait économiser le prix d'une licence pour un connecteur de base de donnée du logiciel de backup ou accélère le temps de restauration des fichiers.

              • [^] # Commentaire supprimé

                Posté par  . Évalué à 3.

                Ce commentaire a été supprimé par l’équipe de modération.

    • [^] # Re: Quelque chose qui m'échappe

      Posté par  (site web personnel) . Évalué à 2.

      Tout dépend du container. Pour le cas de GLPI cela serait les fichiers uploader (factures, contrats…). J'avoue ne pas avoir penser à la solution de sauvegarder le répertoire contenant le volume sur l'hôte. J'ai rapidement été voir et c'est quand même un jolie sac dans le répertoire /var/lib/docker/overlay2. Il y a autant de répertoires que de volumes et comme ça il est difficile de savoir qui appartient à qui. Sans compter les volumes fantômes qui peuvent exister.

      GLPI n'était qu'un exemple et l'idée est d'avoir quelques choses de réutilisable pour d'autres container.

      Pour mysql il est clair qu'il est impossible de copier les fichiers plats, passer par mysqldump permet de mettre un lock le temps de l'export.

      Born to Kill EndUser !

      • [^] # Re: Quelque chose qui m'échappe

        Posté par  (site web personnel, Mastodon) . Évalué à 5. Dernière modification le 10 novembre 2021 à 18:49.

        Si jamais, on peut donner des noms aux volumes et tu retrouveras le dossier avec le nom correspondant sur l'hôte.

        Ça permet aussi de garder un même volume entre plusieurs démarrages de container.

        • [^] # Re: Quelque chose qui m'échappe

          Posté par  . Évalué à 2.

          Ça permet aussi de garder un même volume entre plusieurs démarrages de container.

          D'image plutôt un conteneur ne perds pas son fs lors d'une extinction ou d'un redémarrage.

          https://linuxfr.org/users/barmic/journaux/y-en-a-marre-de-ce-gros-troll

          • [^] # Re: Quelque chose qui m'échappe

            Posté par  (site web personnel, Mastodon) . Évalué à 3. Dernière modification le 12 novembre 2021 à 07:24.

            Une image Docker ne démarre jamais ;-)

            Le volume est attaché au container au moment où tu créés le container.

            Avec un volume nommé, tu peux le réutiliser, même après avoir détruit le container original.

            De même, comme l'a dit PsychoFox plus bas, tu peux l'attacher à plusieurs container en même temps (mais attention à la concurrence d'accès aux fichiers !).

            • [^] # Re: Quelque chose qui m'échappe

              Posté par  . Évalué à 3.

              Le démarrage d'image crée un conteneur. Tu joue sur les mots. Ce que je voulais dire c'est que tu n'a pas besoin de volume pour garder une donnée entre des redémarrages de conteneur.

              https://linuxfr.org/users/barmic/journaux/y-en-a-marre-de-ce-gros-troll

              • [^] # Re: Quelque chose qui m'échappe

                Posté par  (Mastodon) . Évalué à 6.

                Dans les faits t'as tout intérêt à mettre les données dans des volumes séparés des conteneurs car quand tu changes d'image (cas typique de mise à jour), tu remplaces le conteneur par un nouveau.

                • [^] # Re: Quelque chose qui m'échappe

                  Posté par  . Évalué à 2.

                  Oui dans le cas général. Je vois 2 raisons qui font que c'est très utile de garder intact le système de fichier :

                  • pouvoir debuger un conteneur qui est parti en caraphe
                  • garder des données de cache lors de redémarrage

                  https://linuxfr.org/users/barmic/journaux/y-en-a-marre-de-ce-gros-troll

              • [^] # Re: Quelque chose qui m'échappe

                Posté par  . Évalué à 3.

                Non … Une image ne démarre pas … C'est le container démarre en utilisant ue image. Et crois moi, ce n'est pas une question de plaisir de jouer sur les mots. Si tu n'es pas précis sur les termes utilisés en containerisation, tu perds vite les gens (retour d'expérience de deux ans de coaching sur ce genre de techno).

              • [^] # Re: Quelque chose qui m'échappe

                Posté par  (site web personnel, Mastodon) . Évalué à 3.

                Non, non, une image est juste le résultat soit de:

                • la fin d'un build de fichier Dockerfile
                • un commit du système de fichier d'un container

                L'image peut être vu comme un snapshot d'un système de fichier en lecture seule.

                Quand tu "run une image" pour reprendre tes mots, en réalité tu fais ça :

                • tu copies le système de fichier de l'image pour le passer en lecture/écriture pour le container (c'est le container niveau file system)
                • tu attaches les volumes éventuels définis dans la commande "run" (ils sont créés s'ils n'existent pas déjà)
                • tu lies les ports TCP de l'hôte sur ceux du container (si définis)
                • … et d'autres liens entre le namespace du container et l'hôte, je ne connais pas toutes les options…
                • enfin, dernière étape, dans le container une commande est exécutée. Soit celle définie dans la commande "run", soit la ligne CMD du Dockerfile, soit l'ENTRYPOINT de la commande ou du Dockerfile

                Pour le point "copier le système de fichier de l'image", Docker utilise des systèmes de fichiers spécialisés qui ne nécessitent pas de faire une copie réelle, comme BTRFS et OverlayFS.

                Si tu supprimes ton container sans avoir fait un "commit" de son système de fichier (c'est à dire créé une image depuis un système mouvant, c'est une mauvaise idée !) ni avoir mis les données dans un volume, alors tu perds ces données.

                Si tu penses "redémarrer" comme uniquement "stop" et "start", alors oui, les données sont conservées. Mais ce n'est pas le cas intéressant de Docker.

                • [^] # Re: Quelque chose qui m'échappe

                  Posté par  . Évalué à 1.

                  Quand tu "run une image" pour reprendre tes mots[…]

                  Hum https://docs.docker.com/engine/reference/run/

                  $ docker run [OPTIONS] IMAGE[:TAG|@DIGEST] [COMMAND] [ARG...]

                  Si tu penses "redémarrer" comme uniquement "stop" et "start", alors oui, les données sont conservées. Mais ce n'est pas le cas intéressant de Docker.

                  C'est ce que j'avais compris en lisant :

                  Ça permet aussi de garder un même volume entre plusieurs démarrages de container.

                  Je me suis même reposé la question et c'est pour ça que j'ai voulu précisé. Je me suis dis que si moi qui utilise docker régulièrement avait mal compris d'autres pourraient mal comprendre.

                  Me reprendre pour savoir si c'est le fait de lancer une image qui produit un conteneur ou le fait de créer un conteneur qui se base sur une image c'est de la drosophilie avancée.

                  https://linuxfr.org/users/barmic/journaux/y-en-a-marre-de-ce-gros-troll

                  • [^] # Re: Quelque chose qui m'échappe

                    Posté par  (site web personnel, Mastodon) . Évalué à 3.

                    Quand tu "run une image" pour reprendre tes mots[…]

                    Hum https://docs.docker.com/engine/reference/run/

                    $ docker run [OPTIONS] IMAGE[:TAG|@DIGEST] [COMMAND] [ARG…]

                    Et quand tu lis la documentation qui est juste avant:

                    Docker run reference

                    Docker runs processes in isolated containers. A container is a process which runs on a host.

                    Puis, tu lis la documentation juste après:

                    The docker run command must specify an IMAGE to derive the container from.

                    Je suis d'accord que la syntaxe donne l'impression de "run une image", mais en réalité tu run un container.

                    Ce n'est pas de la drosophilie avancée, c'est très important pour comprendre comment Docker fonctionne et comment il faut l'utiliser.

                    Le principe est qu'une image devrait toujours pouvoir être complètement détruite et, quand tu la rebuild avec un Dockerfile, tu retrouves le même résultat à peu près ("à peu près", car ça dépend des commandes exécutées pendant le build).

                    Le container par contre utilise l'image pour exécuter une commande et il n'y a plus de garantie sur l'état du système de fichier du container.

                    Ça permet aussi de garder un même volume entre plusieurs démarrages de container.

                    Je me suis même reposé la question et c'est pour ça que j'ai voulu précisé. Je me suis dis que si moi qui utilise docker régulièrement avait mal compris d'autres pourraient mal comprendre.

                    Ok, cette formulation n'était pas très précise.

                    Le but était surtout de préciser qu'un volume "nommé" a un nom fixe, qu'il peut être facilement identifiable sur la machine hôte.

                    En plus, comme son nom est fixe, il peut aussi facilement être réutilisé après avoir détruit son container. Il peut aussi être lié à d'autres containers (comme proposé par Psychofox pour les backups), mais dans ce cas, il faut faire très attention aux accès concurrents aux fichiers.

                    • [^] # Re: Quelque chose qui m'échappe

                      Posté par  . Évalué à 2.

                      Ce n'est pas de la drosophilie avancée, c'est très important pour comprendre comment Docker fonctionne et comment il faut l'utiliser.

                      Si si si

                      Container images become containers at runtime and in the case of Docker containers - images become containers when they run on Docker Engine.

                      Ce they ce sont les images qui run (Use containers to Build, Share and Run your applications).

                      Le principe est qu'une image devrait toujours pouvoir être complètement détruite et, quand tu la rebuild avec un Dockerfile, tu retrouves le même résultat à peu près ("à peu près", car ça dépend des commandes exécutées pendant le build).

                      Le container par contre utilise l'image pour exécuter une commande et il n'y a plus de garantie sur l'état du système de fichier du container.

                      Reprendre les gens là dessus en allant à l'encontre d'une partie de la documentation ainsi que de l'outillage n'aide en rien.

                      Je sais très bien ce qu'est une image et ce qu'est un container et reprendre des gens sur le fait de décrire la chose de manière active ou passive c'est ridicule et n'aide personne à comprendre le fonctionnement.

                      Le principe est qu'une image devrait toujours pouvoir être complètement détruite et, quand tu la rebuild avec un Dockerfile, tu retrouves le même résultat à peu près ("à peu près", car ça dépend des commandes exécutées pendant le build).

                      Tu n'a donc aucune garanti que cela va produire la même chose. Oui ce serait bien d'avoir des images reproductibles, mais dans la réalité c'est compliqué (tout comme le reste de la chaine de construction). Docker est fait pour ne pas considérer les images comme jetable, mais au contraire pour massivement les réutiliser (c'est entre autre pour ça qu'il y a une distinction entre image et container). Le principe n'est tellement pas de pouvoir détruire une image que le registry docker n'a pas d'API pour supprimer une image. Tu peux la supprimer de ton cache local par contre évidement.

                      https://linuxfr.org/users/barmic/journaux/y-en-a-marre-de-ce-gros-troll

      • [^] # Re: Quelque chose qui m'échappe

        Posté par  (Mastodon) . Évalué à 7.

        J'ai rapidement été voir et c'est quand même un jolie sac dans le répertoire /var/lib/docker/overlay2. Il y a autant de répertoires que de volumes et comme ça il est difficile de savoir qui appartient à qui. Sans compter les volumes fantômes qui peuvent exister.

        En général c'est pas ça qu'on fait. On monte le même volume dans un nouveau container qui fait le copie de backup.

  • # quid de la restauration?

    Posté par  (Mastodon) . Évalué à 4. Dernière modification le 12 novembre 2021 à 11:52.

    Suis-je le seul supris de voir un projet avec un script de backup et absolument rien pour décrire le process de restoration des données?

    Soit dit en passant GLPI est le cas typique d'une appli qui peut souffrir de quelques secondes d'arrêt chaque nuit et pour laquelle il y a peu de chance de vouloir restaurer seulement quelques lignes ou une table. Et ils semble que les volumes semblent être des bind mounts de répertoires de la machine hôte.

    Du coup pourquoi ne pas faire plus simple:
    1. docker-compose stop
    2. snapshot des volumes et montage sur un autre point de montage sur l'hôte
    3. docker-compose up
    4. backup des snapshots
    5. cleanup des snapshots (peut aussi être réalisé en début de point 2 si on peut supporter d'avoir l'espace utilisé et qu'on veut une copie locale de restauration pour des petites bévues)

    L'avantage c'est qu'il n'y a quasi aucun scripting, que t'es absolument sûr que le volume de ta db et du reste de l'appli sont cohérents. Avec ta méthode je ne vois rien qui garantie la cohérence entre le dump mysql et les fichiers copiés. Donc à la restauration tu peux te retrouver avec des fichiers uploadés qui ne sont pas référencés en DB et avoir des trucs pas propres..

    Et pour le restore ce serait aussi très simple:
    - docker-compose stop
    - restoration des données dans le point de montage désiré
    - docker-compose up

    Du reste en utilisant des vrais volumes plutôt que des bind mounts tu pourrais bénéfichier des capacités de snapshots de docker et faire des backups sur des clones.

    • [^] # Re: quid de la restauration?

      Posté par  (Mastodon) . Évalué à 3.

      Oubliez mon dernier point qui n'est valide qu'avec certains pilotes de stockage et pas le projet docker lui-même.

    • [^] # Re: quid de la restauration?

      Posté par  (site web personnel) . Évalué à 2.

      Suis-je le seul supris de voir un projet avec un script de backup et absolument rien pour décrire le process de restoration des données?

      Pour faire la restauration tu utilise BackupPC, mon script permet juste d'extraire des données des containers pour les intégrer dans un processus global de sauvegarde de BackupPC. Dans mon cas j'utilise BackupPC pour Docker, pour des fichiers utilisateurs, pour d'autres bases mysql… Le jour où j'ai besoin de faire une restauration je n'ai pas à me demander par quel outil la sauvegarde est faite et comment cela marche. Des restaurations on en fait pas tout les jours ;)

      Soit dit en passant GLPI est le cas typique d'une appli qui peut souffrir de quelques secondes d'arrêt chaque nuit et pour laquelle il y a peu de chance de vouloir restaurer seulement quelques lignes ou une table. Et ils semble que les volumes semblent être des bind mounts de répertoires de la machine hôte.

      J'ai proposé GLPI, mais ce n'est qu'un exemple, remplace le par ce que tu veux avec ces propres contraintes. Ta proposition est bonne mais comment faire lorsque tu as un container qu'il est totalement impossible de mettre en pause ?

      L'avantage c'est qu'il n'y a quasi aucun scripting, que t'es absolument sûr que le volume de ta db et du reste de l'appli sont cohérents. Avec ta méthode je ne vois rien qui garantie la cohérence entre le dump mysql et les fichiers copiés. Donc à la restauration tu peux te retrouver avec des fichiers uploadés qui ne sont pas référencés en DB et avoir des trucs pas propres..

      Ça oui et effectivement, sauf à mettre en pause ou arrêter le container il n'y a pas de solution. Mais toujours même problème, comment faire pour un container qu'il n'est pas possible d'arrêter ?

      Du reste en utilisant des vrais volumes plutôt que des bind mounts tu pourrais bénéfichier des capacités de snapshots de docker et faire des backups sur des clones.

      J'utilise de vrai volume au quotidien. Si je ne l'ai pas fais dans mon exemple c'est par simplicité et aussi en scriptant la copie des fichiers hors du container on s'affranchit de devoir créer un volume par container.

      Born to Kill EndUser !

      • [^] # Re: quid de la restauration?

        Posté par  (Mastodon) . Évalué à 4.

        Il me semble que tu bottes en touche. Si tu as besoin d'écrire un script spécifique pour que backuppc trouve les données à ingérer, c'est que t'as besoin de faire de même pour recopier les données au bon endroit quand tu restaure…Ton script ne rend pas backuppc omniscient.

Suivre le flux des commentaires

Note : les commentaires appartiennent à celles et ceux qui les ont postés. Nous n’en sommes pas responsables.