Journal [Tuto/HowTo] Sauvegarder les fichiers joints de phpBB3 sur le cloud via rsync et webdav/dafvs2

3
11
jan.
2017

Tuto testé sur : Raspbian Jessie et Xubuntu
L'original de ce tuto est accessible à cette adresse : https://www.0rion.netlib.re/forum4/viewtopic.php?f=63&t=496

Introduction

Pour protéger le forum phpBB3 d'une perte de données (en cas par exemple de mise à jour foirée), il faut maintenir une ou plusieurs copies de la base de données, des fichiers joints et, si vous avez personnalisé votre thème, de vos fichiers styles.
Côté client on va donc utiliser rsync pour sauvegarder les fichiers joints de phpBB (dossier /files/) sur un serveur cloud (nextcloud / owncloud) avec un utilisateur dédié.
Rien ne vous empêche de reproduire cette solution pour d'autres dossiers voire pour tout votre forum si vous le souhaitez.
Vous vous demanderez sans doute "pourquoi ne pas directement le faire avec le client owncloud en ligne de commande" et la réponse tient en une phrase : il est buggé. (voir ce tuto non fonctionnel)

Mise en place

Sur votre serveur cloud (nextcloud / owncloud)

  • Créez un utilisateur dédié avec des droits restreints (Administration - Utilisateurs)
  • Connectez-vous à cet utilisateur et créé un dossier dédié à votre synchronisation (par exemple : phpBB_fichiers_joints)

Sur votre client (le serveur où est hébergé votre forum phpBB)

sudo nano /opt/scripts/synchroCloud.sh

  • Insérez le code suivant en l'adaptant à votre config
#!/bin/bash
# Licence WTFPL - infos : https://www.0rion.netlib.re/forum4/viewtopic.php?f=71&t=496#p1081
# synchronisation des fichiers joints d'un ou plusieurs forum phpBB sur le cloud

montageLocal="/media/montageDistant" #le point de montage locale
dossierDistant="/phpBB_fichiers_joints/" #le dossier destination
monDossier="/var/www/html/forum/files/" #le dossier source
userPourCopie="root" #l'utilisateur a utiliser pour la copie

if [ ! "$SUDO_USER" ]; then
echo "this script need to be lunch by root"
exit 0
fi

   #VERIFICATION DU MONTAGE
startTime=`date +%s`
if [ -d "$montageLocal$dossierDistant" ];then
   endTime=`date +%s`
   runTime=$((endTime-startTime))
   if [ "$runTime" -lt "600" ];then
   #ACTION
           sudo chown www-data:$userPourCopie -R $monDossier & sudo chmod 770 -R $monDossier
              #sauvegarde des fichiers locaux vers cloud
           su $userPourCopie -c "rsync $monDossier $montageLocal$dossierDistant -r"
              #restauration des fichiers depuis le cloud vers local
              #commentez la ligne suivante si vous ne voulez pas de restauration automatique
           su $userPourCopie -c "rsync $montageLocal$dossierDistant $monDossier -r"
              #on reverrouille l'accès au dossier
           sudo chown www-data:root -R $monDossier & sudo chmod 770 -R $monDossier
   else
   echo "$montageLocal => not responding (408) / delais d'attente depasse"
   fi
else
echo "$montageLocal$dossierDistant => not exist"
fi

montageLocal="/media/montageDistant" : le point de montage
dossierDistant="/phpBB_fichiers_joints/" : le dossier destination
monDossier="/var/www/html/forum/files/" : le dossier source
userPourCopie="root" : l’utilisateur a utiliser pour la copie

Note : le script a un soucis d'héritage des variables quand on veut utiliser un utilisateur système dédié (les variables sont créées par root et inaccessible aux autres users)

  • Accordez les bonnes permissions au script
sudo chown root:root /opt/scripts/synchroCloud.sh
sudo chmod 755 /opt/scripts/synchroCloud.sh
  • Ajoutez votre script au cron (tâches planifiées) de votre machine

sudo crontab -e

  • Insérez la ligne suivante en l'adaptant éventuellement

3 0 * * * /opt/scripts/lunchOwncloud.sh
Avec cette commande la tâche sera exécutée une fois par jours a minuit et trois minutes.
Si vous préférez le lancer toutes les heures à la troisième minute, utilisez le cron suivant :

3 * * * *

  • # Cohérence BDD

    Posté par (page perso) . Évalué à 4.

    Salut, y'a rien à faire côté BDD pour s'assurer que le fichier qui contient la base soit bien cohérent (et que la sauvegarde ne tombe pas entre deux opérations sur la BDD)?

    Python 3 - Apprendre à programmer en Python avec PyZo et Jupyter Notebook → https://www.dunod.com/sciences-techniques/python-3

    • [^] # Re: Cohérence BDD

      Posté par (page perso) . Évalué à 3.

      J'ai peut-être pas les yeux en face des trous, mais je ne vois rien concernant la base de données, que ce soit une copie brutale des fichiers, ou un mysqldump. Donc je ne suis même pas certain que cette copie serve à grand-chose.

      • [^] # Re: Cohérence BDD

        Posté par . Évalué à 5.

        Moi non plus je ne vois rien ;)
        Par contre je vois des choses curieuses :
        - Pourquoi lancer deux fois la commande rsync dans un sens puis dans l'autre ?
        - Pourquoi ces commandes chown alors que rsync -a préserve les doits et que le scripts est lancé en root ?

        • [^] # Re: Cohérence BDD

          Posté par . Évalué à 3.

          Pourquoi lancer deux fois la commande rsync dans un sens puis dans l'autre ?

          Le wiki de ubuntu-fr explique que rsync ne fonctionne que dans un sens, si on veut imiter le fonctionnement du client owncloud il faut lancer la commande dans les deux sens. Au départ j'étais parti sur l'utilisation de owncloud-client-cmd mais il est buggé.
          Le but étant qu'en cas de foirage on puisse directement ré-injecter les fichiers automatiquement (surtout que owncloud&nextcloud intègrent une corbeille permettant de restaurer des fichiers supprimé)

          Pourquoi ces commandes chown alors que rsync -a préserve les doits et que le scripts est lancé en root ?

          Au départ le but est de lancer rsync avec un utilisateur non privilégié. (mais j'ai un soucis avec les variables)
          Je dois aussi avouer que j'ai des doutes sur le fonctionnement des droits des fichiers lorsqu'on passe par un montage webdav/davfs2 (si root restaure un fichier depuis le cloud vers local, alors le fichier local appartiendra a root uniquement non?) hors il faut obligatoirement que l'user serveur (www-data) puisse créer/supprimer des fichiers dans /var/www/html/forum/files/

          PS: c'est la première fois que j'utilise rsync, n'hésitez pas a améliorer le script si vous en avez une meilleure compréhension que moi :)

          Merci pour vos retours ;)

          Donation Bitcoin : 1N8QGrhJGWdZNQNSspm3rSGjtXaXv9Ngat

          • [^] # Re: Cohérence BDD

            Posté par . Évalué à 4.

            Le wiki de ubuntu-fr explique que rsync ne fonctionne que dans un sens, si on veut imiter le fonctionnement du client owncloud il faut lancer la commande dans les deux sens.

            Oui mais non.
            Disons que tu lances un rsync de dossier1 vers dossier2 puis de dossier2 vers dossier1.
            * si tu le lances avec --delete, tu vas perdre les fichiers qui existent sur dossier2 et pas sur dossier1 avant la synchro
            * si tu le lances sans --delete, tu ne peux pas supprimer un fichier (sauf à le supprimer dans les 2 dossiers)
            * dans tous les cas, si un fichier est synchronisé, que tu fais une modif sur dossier2, la modif sera écrasée à la prochaine synchro.

            Rsync n'est pas adapté pour de la synchronisation bidirectionnelle. Point.

            Néanmoins, pour du backup, je ne vois pas l'intérêt de faire du bidirectionnel. En revanche, il serait judicieux d'avoir une rétention et ne pas écraser le backup précédent à chaque fois.

            • [^] # Re: Cohérence BDD

              Posté par . Évalué à 1.

              Merci pour tes idées @kna je pense adapter mon script prochainement :)
              Genre ajouter un mode pour sauvegarder entre 1 et X last backup et une sauvegarde de la BDD.

              Néanmoins, pour du backup, je ne vois pas l'intérêt de faire du bidirectionnel.

              En gros ca permet de simplifier la ré-installation/restauration du forum :
              juste copier les fichiers, injecter la BDD puis les fichiers joints reviennent tout seul ^ ^

              Note que se serait une utilisation problématique si on backup en bidirectionnel tout les fichiers du forum (notamment le dossier /cache/).
              Après ce n'est que théorique perso je n'ai activé le backup que du local vers cloud :)

              si tu le lances avec --delete, tu vas perdre les fichiers qui existent sur dossier2 et pas sur dossier1 avant la synchro

              Bon à savoir, rsync n'est pas aussi "intelligent" que le client owncloud (qui lui a une mémoire)

              Donation Bitcoin : 1N8QGrhJGWdZNQNSspm3rSGjtXaXv9Ngat

      • [^] # Re: Cohérence BDD

        Posté par . Évalué à 2. Dernière modification le 12/01/17 à 14:18.

        J'ai peut-être pas les yeux en face des trous, mais je ne vois rien concernant la base de données, que ce soit une copie brutale des fichiers, ou un mysqldump. Donc je ne suis même pas certain que cette copie serve à grand-chose.

        Non ce tuto ne concerne pas la base de données (je suis en train de traiter le sujet, un tuto sur Mysql Cluster est en phase de finalisation et je rédigerai aussi un tuto plus générique pour automatiser un backup BDD de l'un ou l'autre CMS). Mais c'est vrai que j'aurai du l'intégrer directement dans ce tuto ça aurait été plus complet :)

        Cette copie vise à protéger les fichiers joints voir tout les fichiers du forum.
        Pour expliquer cette méthodologie : elle fait suite à un problème que j'ai subis cette semaine : l'update de phpbb vers 3.2 (rhea) qui a foutu en l'air mon forum.

        Comme j'étais persuadé que les fichiers joints étaient stocké en base de données (à cause de l'adresse pour y accéder dont voici un exemple download/file.php?id=468), je n'ai pensé qu'a sauvegarder ma base de données avant de tenter la mise à jours.
        La mise à jours a échoué (j'ai voulu tester la nouvelle méthode via Direct File Access) et ai donc restauré mon forum.
        Après restauration j'ai remarqué que tout était revenu en ordre sauf les fichiers joints qui eux ont disparut. Par contre ils sont encore mentionné dans les threads (exemple).

        Enfaîte phpBB stocke les fichiers joints, renommé avec un identifiant unique, dans le dossier /files/ et dans sa propre base de données il conserve une correspondance.
        Si vous voulez backup votre forum il est donc obligatoire de répliquer la BDD, les fichiers joints brute et tant qu'à faire tout les fichiers que vous avez modifié.

        Donation Bitcoin : 1N8QGrhJGWdZNQNSspm3rSGjtXaXv9Ngat

  • # Nouveau Script

    Posté par . Évalué à 0. Dernière modification le 19/01/17 à 16:06.

    Suite à vos conseils et remarques j'ai recodé le script, que pensez-vous de cette version?

    Cette version va effectuer une copie vers un dossier latest ET un dossier nommé en fonction de la fréquence (hourly, daily, weekly, monthly, yearly) qui doit être passé en paramètre.
    Je me suis inspiré du mode de fonctionnement d'automysqlbackup. Je ne compresse pas les fichiers (sais pas si c'est utile, a vous de voir).

    Cordialement

    #!/bin/bash
    # Licence WTFPL - infos : https://www.0rion.netlib.re/forum4/viewtopic.php?f=71&t=496#p1081
    # synchronisation des fichiers joints d'un ou plusieurs forum phpBB sur le cloud
    # V 1.2 - lancer le software sans paramètre = backup dans dossierDistant/latest et dossierDistant/daily si non ajoutez un des paramètres cron suivant : hourly, daily, weekly, monthly, yearly (dans tout les cas le dossier latest sera update)
    
    montageLocal="/media/montageDistant" #le point de montage locale
    dossierDistant="/phpBB_fichiers_joints" #le dossier destination ne terminez pas par /
    dossierSource="/var/www/html/forum/files/" #le dossier source
    userPourCopie="root" #l'utilisateur a utiliser pour la copie
    
    if [ ! "$SUDO_USER" ]; then
    echo "this script need to be lunch by root"
    exit 0
    fi
    
       #VERIFICATION DU MONTAGE
    startTime=`date +%s`
    if [ -d "$montageLocal$dossierDistant" ];then
       endTime=`date +%s`
       runTime=$((endTime-startTime))
       if [ "$runTime" -lt "600" ];then
    
       #ACTION
    
    
                dossierTemps="/daily/"
    
                case "$1" in
                "hourly")
                    dossierTemps="/hourly/"
                    ;;
                "daily")
                    dossierTemps="/daily/"
                    ;;
                "weekly")
                    dossierTemps="/weekly/"
                    ;;
                "monthly")
                    dossierTemps="/monthly/"
                    ;;
                "yearly")
                    dossierTemps="/yearly/"
                    ;;
                esac
    
                    # VERIF IF DESTINATION FOLDER EXIST IF NOT CREAT IT 
                if ! [ -d "$montageLocal$dossierDistant$dossierTemps" ];then
                        mkdir -p "$montageLocal$dossierDistant$dossierTemps"
                fi
                if ! [ -d "$montageLocal$dossierDistantlatest" ];then
                        mkdir -p "$montageLocal$dossierDistant$dossierDistantlatest"
                fi
    
                sudo chown www-data:$userPourCopie -R $dossierSource & sudo chmod 770 -R $dossierSource
                  #sauvegarde des fichiers locaux vers cloud
    #echo "copie dans $montageLocal$dossierDistant$dossierTemps"
                su $userPourCopie -c "rsync $dossierSource $montageLocal$dossierDistant$dossierTemps -r --delete"
    #echo "copie dans $montageLocal$dossierDistant/latest"
                su $userPourCopie -c "rsync $dossierSource $montageLocal$dossierDistant/latest/ -r --delete"
                  #on reverrouille l'accès au dossier
                sudo chown www-data:root -R $dossierSource & sudo chmod 770 -R $dossierSource
       else
       echo "$montageLocal => not responding (408) / delais d'attente depasse"
       fi
    else
    echo "$montageLocal$dossierDistant => not exist"
    fi

    Donation Bitcoin : 1N8QGrhJGWdZNQNSspm3rSGjtXaXv9Ngat

Suivre le flux des commentaires

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