Manage attachment

L’objectif est très simple, mais répond en même temps à un besoin très fréquent : ajouter dans les emails des fichiers joints.

Ainsi, on rencontrera fréquemment des besoins du type :

  • Ajouter le contenu d’un champ “pièces-jontes” en fichiers joint dans un email (cas traité ici)
  • Générer un fichier (Excel, PDF, …) et directement attacher à chaud ce fichier à un email.

Mise en place

Il faut créer une nouvelle classe d’extension d’email : BaseMailExtension. Cette classe va capter l’évènement beforeSend() afin d’ajouter les pièces jointes dans l’email avant envoi.

L’envoi de l’email ne sera pas bloqué mais, dans le cas d’un champ pièces jointes vide, il aurait pu être imaginé de bloquer l’envoi de l’email en retournant “false”.

L’objet utilisé est le MimeMessage : par défaut, il existe un mime message avec une seule partie, le contenu du message.

Un body peut lui être inséré avec plusieurs parties :

  • Le contenu du message déjà existant
  • Une partie par pièce jointe ajoutée

Il s’agit donc de remplacer le contenu de l’email par le body à plusieurs parties.

Plus techniquement il est possible, dans la construction des “parties de mail” pour les fichiers joints, de récupérer le contenu des “attachments” et de les transférer vers l’email via une DataSource.

Code source

Soit un champ “pièces jointes” nommé “MyAttachmentsProperty”. Ene classe nommée “AttachFileMailExtension” héritant de “BaseMailExtension” doit être créée :

import java.util.Collection;

import javax.activation.DataHandler;
import javax.mail.BodyPart;
import javax.mail.Multipart;
import javax.mail.internet.MimeBodyPart;
import javax.mail.internet.MimeMultipart;
import javax.mail.util.ByteArrayDataSource;

import com.axemble.vdoc.sdk.interfaces.IAttachment;
import com.axemble.vdoc.sdk.mail.extensions.BaseMailExtension;
import com.axemble.vdoc.sdk.utils.Logger;

public class AttachFileMailExtension extends BaseMailExtension {
    protected static final Logger log = Logger.getLogger(AttachFileMailExtension.class);

    /**
     * @see com.axemble.vdoc.sdk.mail.extensions.BaseMailExtension#beforeSend()
     */
    @Override
    protected boolean beforeSend() {
        try {
            Collection<IAttachment> cAttachment = (Collection<IAttachment>) getWorkflowInstance().getValue("MyAttachmentsProperty");
            if ((cAttachment != null) && (!cAttachment.isEmpty())) {
                // Création de la nouvelle structure multipart
                Multipart multipart = new MimeMultipart();

                // Variable de stockage de chaque partie du mail
                BodyPart messageBodyPart;

                /*
                 * 1ere partie du mail = mail d'origine
                 */
                // Nouvelle partie
                messageBodyPart = new MimeBodyPart();
                // Copie du contenu du mail d'origine
                messageBodyPart.setContent(getMessage().getContent(), "text/html");
                // Ajout de cette partie à la structure
                multipart.addBodyPart(messageBodyPart);

                /*
                 * parties suivantes = les pièces jointes
                 */
                for (IAttachment iAttachment : cAttachment) {
                    ByteArrayDataSource bads;
                    try {
                        // On récupère le contenu
                        byte[] tFileContent = iAttachment.getContent();
                        bads = new ByteArrayDataSource(tFileContent, "application/x-any");

                        // On remplit le messageBodyPart
                        messageBodyPart = new MimeBodyPart();
                        messageBodyPart.setHeader("Content-Transfer-Encoding", "binary");
                        messageBodyPart.setDataHandler(new DataHandler(bads));
                        messageBodyPart.setFileName(iAttachment.getName());

                        // Ajout à la structure
                        multipart.addBodyPart(messageBodyPart);
                    } catch (Exception e) {
                        String message = e.getMessage();
                        if (message == null) {
                            message = "";
                        }
                        log.error("Error in AttachFileMailExtension beforeSend method (adding attachment '" + iAttachment.getName() + "') : " + e.getClass() + " - " + message);
                    }
                }

                /*
                 * Finalement on remplace le contenu du mail d'origine par la structure multipart
                 */
                getMessage().setContent(multipart);
            }
        } catch (Exception e) {
            String message = e.getMessage();
            if (message == null) {
                message = "";
            }
            log.error("Error in AttachFileMailExtension beforeSend method : " + e.getClass() + " - " + message);
        }
        return true;
    }

    /**
     * @see com.axemble.vdoc.sdk.mail.extensions.BaseMailExtension#afterSend()
     */
    @Override
    protected void afterSend() {

    }

}

Source : https://wiki.myvdoc.net/xwiki/bin/view/Dev+Floor/HowToSendAGenericResourceMailWithAttachment