Forum Linux.général Imprimer une pièce jointe automatiquement en cli

Posté par  (site web personnel) . Licence CC By‑SA.
Étiquettes : aucune
1
20
oct.
2021

Bonjour à tous,

A l'air du tout numérique j'ai tout de même un besoin qui me parait écologiquement proche de 0 mais c'est un besoin pour remplacer l'antique fax (un bien pour un mal).

Je monte un container docker qui est chargé de relever une boite mail et d'imprimer automatiquement les pièces jointes au format pdf des mails présent. La maquette est monté et cela marche assez facilement.

Fetchmail est chargé toutes les x minutes d'aller chercher les mails en imap. Ensuite un bout de script extrait les pièces jointes et les imprime via rlpr. J'ai juste un problème avec l'archivage. Je souhaiterais faire en sorte que les mails imprimés soient déplacés dans un dossier "archives", ce qui permettrait la connexion via un webmail afin de réaliser des recherches. L'idée n'est pas d'installer un webmail sur le container mais d'utiliser celui de notre fournisseur (OVH).

J'ai testé, sans grande conviction, de créer un répertoire "archives" dans le dossier Mail du container mais bien sûr cela ne synchronise pas avec le serveur. Est-ce qu'il existe quelques choses de léger pour juste faire cette opération ?

Merci d'avance.

  • # utiliser les APIs et les protocoles qui vont bien

    Posté par  . Évalué à 3.

    tu te connectes en IMAP
    il faut donc utiliser les commandes liées à l'IMAP pour creer un dossier et déplacer un email dans ce dossier.

    tout autre moyen sera vouer à l'échec

    • [^] # Re: utiliser les APIs et les protocoles qui vont bien

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

      Effectivement je me connecte en imap mais je ne vois pas comment passer les commandes depuis mon container ?

      Born to Kill EndUser !

      • [^] # Re: utiliser les APIs et les protocoles qui vont bien

        Posté par  . Évalué à 3.

        comment récupères tu les emails ?
        tu utilises fetchmail, regardes les options de ce dernier qui permet peut-être de marquer un email comme lu, de le déplacer

        sinon, tu fais ranger les emails dans les bons dossiers par le serveur,
        puis tu utilises l'option -r ou --folder de fetchmail pour aller lire dans un dossier particulier

        -r <name> | --folder <name>
        (Keyword: folder[s])
        Causes a specified non-default mail folder on the mailserver (or comma-separated list of folders) to be retrieved. The syntax of the folder name is server-dependent. This option is not available under POP3, ETRN, or ODMR.

        autre piste, regarder dans les langages de programmations (python par exemple) comment interagir avec une boite email en IMAP, il y a surement aussi de quoi déplacer un email d'une boite à une autre

        • [^] # Re: utiliser les APIs et les protocoles qui vont bien

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

          Ok merci je vais regarder tout ça.

          Born to Kill EndUser !

        • [^] # Re: utiliser les APIs et les protocoles qui vont bien

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

          D'après ce que j'ai compris --folder de fetchmail permet de dire quel "répertoire" aller relever, donc le répertoire doit être existant dans la BAL. Dans mon cas les nouveaux mails doivent rester à la racine et doivent être déplacé uniquement après traitement (impression).

          fetchmail.conf

          set no syslog
          set logfile /var/log/mail/mail2print.log
          set postmaster "fetchmail"
          
          poll ssl0.ovh.net
            protocol imap
            port 993
            user "XXX@xxxx"
            password "passs"
            ssl
            mda "/usr/bin/procmail -m '/etc/mail2print/procmail.conf'";
          

          procmail.conf

          MAIL_DIR=/home/mail2print/Mail
          VERBOSE=off
          LOGFILE="/var/log/mail/mail2print.log"
          
          :0
          *^content-Type:
          $MAIL_DIR/
          

          J'ai comme l'impression que fetchmail n'est pas capable d'envoyer des commandes, autre que pour relever les mails, au serveur.

          Born to Kill EndUser !

          • [^] # Re: utiliser les APIs et les protocoles qui vont bien

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

            Tu as deux solutions (qui me viennent en tête) :

            • Soit tu dégaines ton langage de prédilection ainsi qu’une librairie pour faire de l’IMAP et accéder à tous tes besoins plus facilement.
            • Soit tu trouves un truc déjà tout fait que tu peux appeler en ligne de commande depuis ton conteneur. P’tet un truc comme https://github.com/Gentux/imap-cli
            • [^] # Re: utiliser les APIs et les protocoles qui vont bien

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

              L'idée de sortir mon python m'a traversé l'esprit mais je trouve dommage de tout refaire "juste" à cause d'un problème de déplacement de mail.

              imap-cli a l'air d'être à l'arrêt et il ne me semble pas gérer les pièces jointes.

              Born to Kill EndUser !

            • [^] # Re: utiliser les APIs et les protocoles qui vont bien

              Posté par  . Évalué à 3.

              De ce que je connais de fetchmail, je ne pense pas qu'il soit possible de lui dire de déplacer les mails récupérés dans un dossier IMAP spécifique.
              En revanche, cela doit être possible avec getmail qui possède une option de configuration move_on_delete (la façon de configurer m'a un peu surpris : il faut demander la suppression des mails récupérés en indiquant que ces mails supprimés doivent être déplacés…) Évidemment, dans ce cas, le mail est déplacé au moment où on le récupère, pas après analyse et impression des pièces jointes. Pour cela, on n'échappera pas à l'utilisation d'un client IMAP (api ou cli) et ça va forcément se compliquer un peu (il faudra avoir un identifiant du mail pour savoir quoi déplacer).

              • [^] # Re: utiliser les APIs et les protocoles qui vont bien

                Posté par  (site web personnel) . Évalué à 4. Dernière modification le 22 octobre 2021 à 11:19.

                Nikel avec getmail

                fichier de config

                [retriever]
                    type = SimpleIMAPRetriever 
                    server = server
                    username = username
                    password = password
                    mailboxes = ("INBOX",)
                    move_on_delete = INBOX.INBOX.archives 
                
                [destination]
                    type = Maildir
                    path = /home/mail2print/Mail/
                
                [options]
                    delete = true
                    delete_after = 0
                    read_all = false
                    keep = true

                Dans mon container je lance toute les x minutes getmail par cette commande

                    #!/bin/sh
                    TIMECRON1=${TIMECRON:-300}
                
                    while :
                    do
                            getmail --getmaildir=/etc/mail2print --rcfile=getmail.conf
                            sh /bin/printmail.sh
                            sleep $TIMECRON1
                    done

                getmail "copie" les mails dans le répertoire Mail/new, efface le mail de INBOX pour le copier dans INBOX.INBOX.archives

                Ensuite le script suivant extrait les fichiers joints, lance l'impression et fait le ménage dans les répertoires.

                    #!/bin/bash
                    # Parameters
                    MAILDIR=/home/mail2print/Mail
                    LOGFILE=/var/log/mail/mail2print.log
                    ATTACH_DIR=/home/mail2print/Mail/attachments
                    PRINTER=${PRINTER}
                
                    if [ -d ${MAILDIR}/new ]
                    then
                            COUNT=`ls ${MAILDIR}/new | wc -l`
                            if [ ${COUNT} -ne 0 ]
                            then
                                    for i in ${MAILDIR}/new/*
                                    do
                                            #echo "[printmail] Processing : $i" | tee -a ${LOGFILE}
                                            uudeview $i -iqn -p ${ATTACH_DIR}/
                
                                            # process file attachments with space
                                            cd ${ATTACH_DIR}
                                            NBATTACH=`ls ${ATTACH_DIR} | wc -l`
                                            if [ ${NBATTACH} -ne 0 ]
                                            then
                                                    for e in ./*
                                                    do
                                                            a=`echo $e | tr "[:blank:]" "_"`
                                                            if [ $? -eq 0 ]
                                                            then
                                                                    mv "$e" "$a"
                                                            fi
                                                    done
                                                    for f in *.PDF
                                                    do
                                                            mv $f ${f%.*}.pdf
                                                    done
                
                                                    # end of patch
                                                    #echo "[printmail] Printing PDFs" | tee -a ${LOGFILE}
                                                    for x in ${ATTACH_DIR}/*.pdf
                                                    do
                                                            #echo "[printmail] Printing : $x" | tee -a ${LOGFILE}
                                                            rlpr --printer=${PRINTER} $x
                                                            #echo "[printmail] Deleting file : $x" | tee -a ${LOGFILE}
                                                            rm -f $x | tee -a ${LOGFILE}
                                                    done
                
                                                    #echo "[printmail] Clean up and remove any other attachments" | tee -a ${LOGFILE}
                                                    for y in ${ATTACH_DIR}/*
                                                    do
                                                            rm -f $y
                                                    done
                                            fi
                
                    #                       # delete mail
                                            #echo "[printmail] Deleting mail : $i" | tee -a ${LOGFILE}
                                            rm $i | tee -a ${LOGFILE}
                                    done
                            fi
                    fi

                Faut que j'intègre la suppression du fichier log tout les x jours et éventuellement une purge du dossier INBOX.INBOX.archives tout les x mois.

                Au final j'utilise un seul programme getmail totalement intégré au système. Je vais voir pour publier tout ça sur docker hub et github.

                Born to Kill EndUser !

                • [^] # Re: utiliser les APIs et les protocoles qui vont bien

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

                  Et voilà le petit dépôt qui va bien pour les warrior : https://github.com/Philippe-M/mail2print

                  Born to Kill EndUser !

                • [^] # Re: utiliser les APIs et les protocoles qui vont bien

                  Posté par  . Évalué à 4. Dernière modification le 22 octobre 2021 à 11:34.

                  amelioration pour optimiser tout ca

                  1°) tu rentres dans le dossier ATTACH
                  mais tu listes ce meme dossier pour compter les occurences
                  un simple ls puisque tu es dedans serait suffisant

                  2°) tes variables e,a,y,f ne sont pas parlantes

                  3°) tu boucles souvent pour relire chacun des fichiers (avant conversion, avant patch, apres patch pour impression

                  pourquoi ne pas prendre le fichier, le patcher, l'imprimer dans une seule boucle et passer au suivant

                  dans mon code il faut surement revoir la condition (if extension = pdf), j'ai un doute sur la syntaxe et pas le temps de verifier

                  # process file attachments
                  for e in ./*
                  do
                   # calcul le nouveau nom en replaçant les espaces par _ et PDF par pdf
                   nouveau_nom=`echo $e | tr "[:blank:]" "_" | tr "PDF" "pdf"`
                   # extrait l'extension
                   extension=${nouveau_nom##*.}
                   # renomme sous la nouvelle nomenclature
                   mv $e $nouveau_nom
                   # regarde si c'est un PDF et l'imprime
                   if [[ ${extension} = 'pdf' ]]
                      rlpr --printer=${PRINTER} $nouveau_nom 
                   fi
                   # efface la piece jointe
                   rm -f `{mathjax} nouveau_nom | tee -a `{LOGFILE}
                  done
                  • [^] # Re: utiliser les APIs et les protocoles qui vont bien

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

                    Effectivement, c'est bien plus propre comme tu le propose.

                    Merci.

                    Born to Kill EndUser !

                  • [^] # Re: utiliser les APIs et les protocoles qui vont bien

                    Posté par  (site web personnel) . Évalué à 2. Dernière modification le 22 octobre 2021 à 15:01.

                    Version corrigé, il y avait un problème avec le mv qui n'aimais pas trop les espaces dans le nom de fichier initial.

                    for e in ./*
                    do
                      # calcul le nouveau nom en replaçant les espaces par _ et PDF par pdf
                      nouveau_nom=`echo $(basename "$e") | tr "[:blank:]" "_" | tr "PDF" "pdf"`
                    
                      # extrait l'extension
                      extension=${nouveau_nom##*.}
                    
                      # renomme sous la nouvelle nomenclature
                      mv "$(basename "$e")" $nouveau_nom
                    
                      # regarde si c'est un PDF et l'imprime
                      if [ ${extension} = "pdf" ]
                      then
                        rlpr --printer=${PRINTER} $nouveau_nom
                      fi
                    
                      # efface la piece jointe
                      rm -f $nouveau_nom
                    done

                    Born to Kill EndUser !

                    • [^] # Re: utiliser les APIs et les protocoles qui vont bien

                      Posté par  . Évalué à 2.

                      alors c'est dommage d'appeler 2fois basename

                      autant faire

                      fichier="$(basename ${e})"

                      puis utiliser la variable ${fichier} partout ou l'ancien nom doit etre utiliser

                      ah, aussi quand tu colles du code, le bouton de l'éditeur n'est pas complet, il faut preciser le langage pour que ca colore le code suivant le langage.

                      ainsi :

                      ```sh
                      #!/bin/bash

                      #mon code shell

                      if action
                      then
                      reaction1
                      reaction2
                      fi
                      ```

                      donne

                      #!/bin/bash
                      
                      #mon code shell
                      if action
                      then
                        reaction1
                        reaction2
                      fi

Suivre le flux des commentaires

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