Drupal  8 : l'envoi de mails sous toutes les coutures

Des mouettes et des pigeons sur la rambarde d'un pont

Par défaut, tous les mails envoyés par Drupal 8 le sont en texte brut. Pour envoyer des mails en HTML, que ce soit pour des newsletters, ou encore tout simplement pour les différentes notifications afin de les enrichir quelque peu, il est nécessaire de modifier le système d'envoi par défaut des courriers électroniques, ou encore d'en utiliser un autre. Le moyen le plus simple est d'utiliser un des modules permettant l'envoi de mails HTML, tels que SwiftMailer, HTMLMail ou encore MimeMail pour ne citer que les plus connus (tous ne disposent pas encore d'une version stable Drupal 8 à l'heure actuelle).

Ces modules ont aussi pour particularité d'être basé sur le Module Mail System qui offre une interface graphique permettant de modifier simplement le système d'envoi des mails et utiliser tel ou tel module pour assurer ou bien le formatage des courriers ou bien leur envoi. Ce module permet de spécifier également plusieurs interfaces chargées de l'envoi de mails en fonction du module responsable de l'envoi, ou encore de la clé utilisée pour générer un mail, ou bien un mixte des deux.

Par contre ces modules peuvent devenir limitant si nous souhaitons envoyer des mails de façon programmatique, afin de récupérer plus facilement un certain nombre de données par exemple, ou, lors de l'envoi d'un grand nombre de courriers, si nous souhaitons utiliser le système de Cron pour limiter et répartir la charge lors de ces envois.

Faisons un tour d'horizon du système d'envoi des courriers électroniques de Drupal 8. Cela est utile à plus d'un titre. Bien sûr si nous avons besoin de réaliser un envoi programmatique, mais aussi pour mieux comprendre le mécanisme général et donc le fonctionnement des différents modules disponibles pour réaliser cette tache.

Schéma général

L'envoi d'un mail avec Drupal 8 est assez similaire à celui en place avec Drupal 7.

Il se réalise en 6 étapes principales.

Schéma général d'envoi d'un mail avec Drupal 8

Etape 1 : Déclenchement de l' envoi du mail avec le service MailManager.

Nous déclenchons l'envoi d'un mail avec le service MailManager et sa méthode mail().

\Drupal::service('plugin.manager.mail')->mail()

Etape 2 : Préparation du mail

Le HOOK hook_mail() permet de préparer le contenu du message en fonction des différents paramètres passés au service MailManager. C'est à cette étape également que nous pouvons préparer les différents headers du mail sortant, dont par exemple le Content-Type.

Etape 3 : Altération possible du mail

Tout module peut altérer un mail avant qu'il soit transmis, voir annuler son envoi, en implémentant hook_mail_alter().

Etape 4 : Sélection du plugin responsable de l'envoi du mail. Par défaut le Plugin PHPMail est utilisé pour tous les mails émis.

Drupal 8 peut disposer de plusieurs interfaces chargées de l'envoi des mails. Nous pouvons par exemple avoir une interface pour l'envoi de mails avec Mandrill, ou SwiftMailer, ou la fonction native de PHP, etc. C'est à cette étape que le Plugin responsable de l'envoi du mail est sélectionné, sur la base des paramètres $module et $key passés au service MailManager à l'étape 1.

Etape 5 : Le Plugin réalise le formatage du mail

La mise en forme du champ body du mail est réalisée par la méthode format() de l'interface MailInterface. C'est à cet étape que le corps du mail est formatté pour être rendu soit en texte brut, soit au format HTML.

Etape 6 : Le Plugin procède à l'envoi du mail

Le mail est envoyé en utilisant le service implémenté par la méthode mail() de l'interface MailInterface.

Cette dernière méthode retourne le résultat du mail envoyé, ou en cas d'impossibilité d'envoi, une erreur.

 

Regardons un peu plus en détail chaque phase du cheminement d'un mail envoyé par Drupal 8. Et profitons-en pour réaliser notre envoi de mail au format HTML et non plus au format texte brut par défaut.

Le déclenchement de l'envoi du mail

Le déclenchement de l'envoi d'un mail peut être réalisé de multiples manières. Par des modules implémentant des notifications mail (Contact, Simple News, etc.), avec Rules, ou encore de façon programmatique. C'est cette dernière méthode que nous allons explorer plus en détail.

$sitename = \Drupal::config('system.site')->get('name');
$langcode = \Drupal::config('system.site')->get('langcode');
$module = 'my_module';
$key = 'my_key';
$to = $account->getEmail();
$reply = NULL;
$send = TRUE;

$params['message'] = t('Your wonderful message about @sitename', array('@sitename' => $sitename));
$params['subject'] = t('Message subject');
$params['options']['username'] = $account->getUsername();
$params['options']['title'] = t('Your wonderful title');
$params['options']['footer'] = t('Your wonderful footer');

$mailManager = \Drupal::service('plugin.manager.mail');
$mailManager->mail($module, $key, $to, $langcode, $params, $reply, $send);

L'envoi d'un mail est réalisé avec le service plugin.manager.mail avec sa méthode mail(). Cette méthode requiert quelques paramètres obligatoires :

  • le paramètre $module qui servira ultérieurement à la sélection du Plugin responsable de l'envoi du mail. Dans le cas de mails envoyés avec des modules contribués, ce paramètre est renseigné par le module qui a réalisé l'envoi.
  • Le paramètre $key qui va permettre de cibler précisément ce mail dans sa phase de préparation ou d'altération. Ce paramètre peut aussi être utilisé dans la sélection du Plugin (cf. Etape 4)
  • Le paramètre $to qui est le destinataire du mail
  • Le paramètre $langcode correspond à la langue dans lequel le mail doit être envoyé. Nous prenons ici la langue courante du site. Il pourrait être plus pertinent d'utiliser la langue par défaut sélectionnée par l'utilisateur depuis son compte.
  • Le tableau $params peut contenir autant de données que nécessaires. En règle générale il contient à minima le corps du mail (ici dans la variable $params['message']
  • Les deux derniers paramètres $reply et $send permettent de spécifier respectivement l'adresse mail de réponse, et de demander l'envoi du mail. Ce dernier paramètre $send peut par exemple être utilisé dans la phase d'altération (Etape 3)  pour annuler l'envoi du mail sous certaines conditions.

Dans notre exemple ci-dessus nous définissons quelques paramètres supplémentaires avec $params['options'] pour enrichir notre mail. Ces paramètres sont tout à fait optionnels, et c'est aussi une des facilités offertes par un envoi programmatique : associer au mail un ensemble de données complémentaires qui pourront être utilisées pour construire son corps de texte.

La préparation du mail

Le contenu du mail, ainsi que ses entêtes, est préparé durant cette phase, en implémentant hook_mail().

/**
 * Implements hook_mail().
 */
function my_module_mail($key, &$message, $params) {
  switch ($key) {
    case 'my_key':
      $message['from'] = \Drupal::config('system.site')->get('mail');
      $message['headers']['Content-Type'] = 'text/html; charset=UTF-8; format=flowed; delsp=yes';
      $message['subject'] = $params['subject'];
      $message['body'][] = $params['message'];
      $message['options'] = [];
      if (isset($params['options']) && !empty($params['options'])) {
        foreach ($params['options'] as $key => $value) {
          $message['options'][$key] = $value;
        }
      }
      break;
  }
}

Nous préparons ici le mail et lui attribuons une adresse d'expéditeur, un Content-Type pour spécifier qu'il s'agit d'un mail au format HTML, et renseignons les 2 principaux contenus d'un mail : son objet et son corps de texte.

Nous récupérons également les différents paramètres passés en option pour les affecter à la variable $message qui sera transmise au Plugin chargé de son formatage et de son envoi. Nous pourrions également dans cette phase renseigner également les entêtes du mail pour par exemple modifier l'adresse mail de réponse si nous souhaitons qu'elle soit différente de celle de l'expéditeur.

L'altération du mail

Tout module peut ici altérer le contenu d'un mail, voire annuler son envoi, en implémentant hook_mail_alter(), avant qu'il ne soit transmis au Plugin pour formatage et envoi. Par exemple :

/**
 * Implements hook_mail_alter().
 */
function another_module_mail_alter(&$message) {
  switch ($message['key']) {
    case 'my_key':
      if ( /* Some conditions. */ ) {
        $message['body'][] = t('Additionnal message');
      }
      if ( /* Another condition. */ ) {
        $message['send'] = FALSE;
      }
      break;
  }
}

Nous pouvons ici rajouter du contenu au corps du mail, ou encore sous certaines conditions annuler l'envoi de ce dernier, modifier ses entêtes, etc.

La sélection du Plugin

Le formatage et l'envoi du mail proprement dit est assuré par un Plugin de Drupal 8, implémentant MailInterface. Par défault le seul Plugin disponible est PHPMail qui permet d'envoyer des mails au format texte brut.

Pour ajouter un nouveau Plugin, il nous faut le déclarer dans la configuration system.mail de notre site. Cette déclaration doit être réalisée au moment de l'installation de notre module. Il nous faut donc utiliser hook_install(), dans le fichier my_module.install de notre module.

/**
 * Implements hook_install().
 */
function my_module_install() {
  $config = \Drupal::configFactory()->getEditable('system.mail');
  $mail_plugins = $config->get('interface');
  if (in_array('my_module', array_keys($mail_plugins))) {
    return;
  }

  $mail_plugins['my_module'] = 'my_module_mail';
  $config->set('interface', $mail_plugins)->save();
}

Que faisons-nous ? Nous chargeons la configuration des interfaces Mail de notre site, et rajoutons au tableau $mail_plugins une valeur sous la forme $mail_plugin['key'] = 'value'.

La sélection du Plugin adéquat pour envoyer un mail va s'effectuer sur la base de la clé key ajoutée à notre configuration (dans notre exemple my_module). Cette clé peut avoir pour valeur soit le nom du module, soit le nom d'une clé (utilisée pour le déclenchement de l'envoi d'un mail, my_key dans notre exemple à l'étape 1), soit une concaténation des deux.

Ainsi, lors de l'étape 1, lorsque nous déclenchons l'envoi d'un mail, en spécifiant les paramètres $module et $key, nous ciblons alors un Plugin particulier à utiliser. Si aucune valeur correspondante n'est trouvée dans la configuration des interfaces, alors c'est le Plugin par défaut qui est utilisé.

La valeur affectée value à notre clé correspond à l'identifiant du Plugin Mail qui devra être chargé pour procéder au formatage et à l'envoi du mail.

Dernier point très important. Il est impératif de supprimer notre Plugin Mail de la configuration des interfaces Mail de Drupal 8 si le module est désinstallé. Pour ce il nous suffit d'implementer hook_unistall().  

/**
 * Implements hook_uninstall().
 */
function my_module_uninstall() {
  $config = \Drupal::configFactory()->getEditable('system.mail');
  $mail_plugins = $config->get('interface');
  if (!in_array('my_module', array_keys($mail_plugins))) {
    return;
  }

  unset($mail_plugins['my_module']);
  $config->set('interface', $mail_plugins)->save();
}

Il ne nous reste plus qu'à créer notre Plugin Mail pour assurer l'envoi proprement dit, nous permettant de maîtriser l'ensemble de la chaîne d'envoi.

La création du Plugin Mail

Pour créer notre Plugin, rien de plus simple. Il nous suffit de créer un fichier sous l'arborescence src/Plugin/Mail/MyModuleMail.php de notre module.

**
 * @file
 * Contains \Drupal\my_module\Plugin\Mail\MyModuleMail.
 */
namespace Drupal\my_module\Plugin\Mail;

use Drupal\Core\Mail\MailInterface;
use Drupal\Core\Mail\Plugin\Mail\PhpMail;
use Drupal\Core\Render\Markup;
use Drupal\Core\Site\Settings;
use Drupal\Component\Render\MarkupInterface;
use Drupal\Component\Utility\Html;
use Drupal\Core\Render\Renderer;
use Symfony\Component\DependencyInjection\ContainerInterface;
use Drupal\Core\Plugin\ContainerFactoryPluginInterface;

/**
 * Defines the plugin Mail.
 *
 * @Mail(
 *   id = "my_module_mail",
 *   label = @Translation("My Module HTML mailer"),
 *   description = @Translation("Sends an HTML email")
 * )
 */
class MyModuleMail extends PHPMail implements MailInterface, ContainerFactoryPluginInterface {

  /**
   * @var \Drupal\Core\Render\Renderer;
   */
  protected $renderer;

  /**
   * MyModuleMail constructor.
   *
   * @param \Drupal\Core\Render\Renderer $renderer
   *   The service renderer.
   */
  function __construct(Renderer $renderer) {
    $this->renderer = $renderer;
  }

  /**
   * {@inheritdoc}
   */
  public static function create(ContainerInterface $container, array $configuration, $plugin_id, $plugin_definition) {
    return new static(
      $container->get('renderer')
    );
  }

Vous noterez l'identifiant du Plugin déclaré dans les annotations du Plugin. C'est ce même identifiant que nous avons déclaré dans la configuration des interfaces Mail à l'étape précédente.

Pour notre cas de figure nous étendons le Plugin existant PHPMail pour utiliser sa méthode d'envoi, celle native à PHP. Nous aurons besoin de surcharger uniquement le formatage du mail pour rendre celui-ci au format HTML. Si nous souhaitons utiliser une autre méthode d'envoi, il n'est bien sûr pas nécessaire d'étendre PHPMail. 

A noter aussi, nous récupérons le service Renderer par injection de dépendance. C'est la raison pour laquelle notre Plugin implémente ContainerFactoryPluginInterface

Passons maintenant à ce qui nous intéresse en premier lieu, le formatage de notre mail.

Le formatage du mail

Cette phase nous permet de construire, à proprement parler, le contenu intégral du corps de texte du mail. Jusqu'à présent nous avons passé en paramètre aux différentes fonctions appelées des éléments sur son contenu. Il ne reste plus qu'à le mettre en forme, et essayer d'obtenir un rendu consistant sur tous les clients de messagerie électronique.

Nous créons donc la fonction format() au sein de notre Plugin, qui pourrait ressembler à cela.

/**
 * {@inheritdoc}
 */
public function format(array $message) {
  
  $message = $this->cleanBody($message);
  $message['options']['texte'] = $message['body'];

  $render = [
    '#theme' => 'my_module_courriel',
    '#message' => $message,
  ];
  $message['body'] = $this->renderer->renderRoot($render);
  return $message;
}

Le but de cette méthode est de transmettre tous les éléments de contenu à un template Twig qui va nous permettre de construire tout le rendu HTML du corps de notre mail.

Nous utilisons en premier lieu une méthode interne à notre Plugin pour transformer les différents textes ajoutés à la variable $message['body'] en tableau pouvant être rendu (renderable arrays), et désinfecté le cas échéant, par le moteur de template Twig. 

Nous affectons ce texte, désormais sain (i.e. n'offrant pas de vecteurs d'attaque XSS par exemple), à la variable $message['options']['texte'].

Puis nous utilisons le service Renderer pour construire la structure finale du HTML à inclure dans le corps du mail, en utilisant donc le template my_module_courriel, structure finale que nous ré-affectons à notre variable $message['body'] qui va être envoyée en tant que corps du mail.

Cela suppose que nous ayons au préalable implémenté hook_theme pour déclarer notre thème.

/**
 * Implements hook_theme().
 */
function my_module_theme($existing, $type, $theme, $path) {
  return [
    'my_module_courriel' => [
      'template' => 'mail',
      'variables' => [
        'message' => array(),
      ],
    ],
  ];
}

Nous pouvons aussi déclarer une fonction de preprocess pour notre template my_module_mail déclaré, afin de préparer quelque peu les variables passées, voire pour une dernière fois les altérer.

function template_preprocess_my_module_courriel(&$variables) {
  if (isset($variables['message']['options']) && !empty($variables['message']['options'])) {
    foreach ($variables['message']['options'] as $key => $value) {
      $variables[$key] = $value;
    }
  }
}

Et il ne reste plus qu'à utiliser un template Twig, qui se chargera au passage d'assurer un rendu sain grâce à la désinfection des éléments activée par défaut. Nous pouvons utiliser alors un des nombreux templates responsives de mail disponibles sur l'Internet. Le template ci-dessous va par exemple afficher les variables username, title, footer passés en paramètre à l'étape 1, et bien entendu le texte principal passée à la variable texte.

{# File mail.html.twig #}
<!doctype html>
<html>
<head>
  <meta name="viewport" content="width=device-width">
  <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
  <title>{{ title }}</title>
</head>

<body>

<!-- body -->
<table>
  <tr>
    <td>
      <!-- content -->
      <div class="content">
        <table>
          <tr>
            <td>
              {% if title %}
                <h1>{{ title }}</h1>
              {% endif %}

              {% if username %}
                <p>Bonjour {{ username }},</p>
              {% else %}
                <p>Bonjour,</p>
              {% endif %}

              {% if texte %}
                <p>{{ texte }}</p>
              {% endif %}

            </td>
          </tr>
        </table>
      </div>
      <!-- /content -->
    </td>
  </tr>
</table>
<!-- /body -->

{% if footer %}
<!-- footer -->
<table class="footer-wrap">
  <tr>
    <td class="container">
      <!-- content -->
      <div class="content">
        <table>
          <tr>
            <td align="center">
              <p>{{ footer }}</p>
            </td>
          </tr>
        </table>
      </div>
      <!-- /content -->
    </td>
  </tr>
</table>
<!-- /footer -->
{% endif %}

</body>
</html>

Vous pouvez alors contôler très finement quels contenus seront rendus et dans quelle zone de votre mail. Vous remarquerez l'utilisation extensive de l'élément table. Je crois que l'on a pas encore mieux en 2016 pour s'assurer d'un rendu homogène, et responsive, sur tous les types de client de messagerie. A moins que vous n'ayez quelques pistes fraiches ? N'hésitez pas à les partager dans les commentaires. 

Nous avons formatté notre mail au format HTML. Il ne nous reste qu'à l'envoyer.

L'envoi du mail

Tout simplement nous allons utiliser la fonction native de PHP utilisée par le Plugin par défaut PHPMail.

/**
 * {@inheritdoc}
 */
public function mail(array $message) {
  return parent::mail($message);
}

Si nous souhaitons utiliser un autre service d'envoi de mail, tel que Mandrill, ou un MTA local, nous pouvons le déclarer au sein de cette méthode. Vous trouverez par exemple une parfaite illustration dans ce billet Using and Extending the Drupal 8 Mail API: Part 2 pour utiliser Mandrill comme système d'envoi.

C'est parti !

Après ce long (trop long ?) billet, nous avons implémenté notre propre Plugin de Mail. Mais encore une fois, c'est une des méthodes (sans doute la plus fine car elle permet de contrôler toute la chaîne de production du mail) et non la seule, heureusement.

Le module SwiftMailer dispose d'une version déjà  fonctionnelle sur Drupal 8 (les modules MimeMail ou HTMLMail ne devraient pas tarder) et vous pourrez mieux saisir les options de configuration, que ce soit de ce module, ou du module Mail System permettant la configuration et le choix des méthodes de formatage et d'envoi des mails.

Il n'est d'ailleurs pas interdit de coupler à la fois la richesse fonctionnelle de SwiftMailer (qui fait un peu plus que le formatage, en gérant également l'attachement des pièces jointes, ou en injectant dans le corps du mail les images présentes dans le contenu) et une partie des différents mécanismes décrits dans ce billet. Drupal 8 offre toute une panoplie d'outils pour arriver à personnaliser aisément les courriers et contôler toute la chaîne d'envoi.

Vous souhaitez mieux maîtriser les mails qui sont émis pour votre site. Vous avez une problématique avec ces derniers ? N'hésitez pas à consulter un expert Drupal 8

 

Commentaires

Soumis par Noé (non vérifié) le 20/04/2016 à 09:39 - Permalien

Où se place le code dans la partie "Le déclenchement de l'envoi du mail" ? Dans le nom_module.module ? Dans le hook_entity_insert() ?

On peut l'utiliser dans n'importe quel hook (hook_entity_insert(), hook_entity_update(), etc.), ou fonction de submit, ou une Class, pour réagir à un événement. L'envoi du mail est réalisé forcément en fonction d'un événement (tout du moins dans 95% des cas), il faut donc placer cette partie de code dans le hook ou la fonction correspondante à cet événement.

Soumis par hanen (non vérifié) le 01/05/2016 à 01:19 - Permalien

La méthode "cleanBody($message)" dans la fonction "public function format(array $message)" est non définie dans cette classe. Où elle est déclarée !!!??

Bonjour. Tout d'abord merci pour votre question. Cette méthode est à déclarer bien sûr dans la Class. Pour des raisons de lisibilité, et ne pas surcharger inutilement le billet (déjà long), elle n'est pas détaillée dans l'article.

Soumis par flo (non vérifié) le 01/05/2017 à 16:43 - Permalien

J'essaie depuis 2 jours d'installer swiftmailer et sa librairie ou plutôt sa librairie pour pouvoir activer swiftmailer ensuite sous D8 mais novice, je bute. Rien n'y fait et je suis perdue. Pourriez-vous m'aider s'il vous plait? Merci par avance.
Florence

Pour installer swiftmailer et ses dépendances, il vous suffit d'executer la commande composer require drupal/swifmailer ~1.0. Sinon vous devez télécharger une à une les dépendances du module swiftmailer (que vous trouverez dans le fichier composer.json du module) et les placer dans le répertoire vendor.

Soumis par Stephane (non vérifié) le 05/07/2017 à 11:12 - Permalien

Bonjour,
Je débute avec Drupal et j'utilise workbench (access et moderation) et je me demandais s'il était possible d'intégrer l’étape de déclenchement de l'envoi du mail dans workbench moderation.
Mon but étant d'envoyer un mail a tous les utilisateurs ayant le rôle modérateur dès que tu contenu passe au statut "a modérer".

Bonjour, je n'ai pas encore utilisé workbench moderation sur Drupal 8, mais s'il utilise les event dispatcher pour ses changements d'état vous pouvez souscrire à ces événements pour déclencher l'envoi d'un email. Ou même au pire depuis un hook_entity_presave(). Mais il y a aussi des modules qui peuvent cela comme workbench_email, mais je ne connais pas son état sur Drupal 8 (il est en version alpha5).

Soumis par Tom (non vérifié) le 13/07/2017 à 14:50 - Permalien

Bonjour,

J'ai créé un module de formulaire personnalisé et je ne parviens pas à faire le lien entre ma fonction qui déclenche l'envoie du mail et celle qui prépare le mail. Le mail est du coup envoyé mais sans sujet ni contenu.
Voilà mes deux fonctions :

/**
* Implements hook_mail().
*/
function custom_forms_mail($key, &$message, $params)
{
$options = array(
'langcode' => $message['langcode'],
);
switch ($key) {
case 'submit_form':
$message['from'] = \Drupal::config('system.site')->get('mail');
$message['subject'] = 'Sujet test';
$message['body'][] = Html::escape($params['message']);
break;
}
}

-------------------------------------------------------------------------------------------------

public function submitForm(array &$form, FormStateInterface $form_state) {
$mailManager = \Drupal::service('plugin.manager.mail');
$module = 'custom_forms';
$key = 'submit_form'; // Replace with Your key
$to = \Drupal::currentUser()->getEmail();
$params['message'] = 'Message test';
$params['title'] = 'Title';
$langcode = \Drupal::currentUser()->getPreferredLangcode();
$send = true;

$result = $mailManager->mail($module, $key, $to, $langcode, $params, NULL, $send);
if ($result['result'] != true) {
$message = t('There was a problem sending your email notification to @email.', array('@email' => $to));
drupal_set_message($message, 'error');
\Drupal::logger('mail-log')->error($message);
return;
}

$message = t('An email notification has been sent to @email ', array('@email' => $to));
drupal_set_message($message);
\Drupal::logger('mail-log')->notice($message);
}

Je ne comprends pas ce que j'ai pu oublier. Y a il une manipulation à faire autre que de spécifier le nom du module dans la fonction qui déclenche l'envoi du mail pour faire le lien avec celle qui prépare le mail?

Merci d'avance,

Rebonjour,

En fait j'ai trouvé réponse à ma question, ma fonction qui implémentait le hook_mail se trouvait dans le controleur de mon formulaire, je n'avais pas compris qu'elle devait se trouver dans mon custom_forms.module pour être appelée.

Merci quand même,

Tom

Soumis par Lu (non vérifié) le 06/09/2017 à 10:13 - Permalien

Bonjour ! Merci pour ce billet très utile. J'ai néanmoins une question :
Sur Drupal 8, j'ai installé Swiftmailer afin d'envoyer des mails html customizés depuis un module custom. J'ai suivi les premières étapes de ton article mais je ne sais pas où placer la méthode format() et tout ce qui concerne l'aspect du mail.
En effet, lorsque j'ai installé Swiftmailer, je me suis aperçue en configurant le mail system que j'avais déjà accès au plugin swift sans avoir besoin de suivre l'étape de sélection/création de plugin que tu proposes.
Je n'ai fait qu'un appel classique de Drupal mail() dans mon contrôleur et une fonction hook_mail() dans mon .module, comme tu l'expliques dans tes deux premières étapes, et j'ai configuré le mail system pour que le "formatter" et le "sender" soit Swift.

Mes mails sont bien envoyés par Swift au format html mais n'ont pour l'instant aucun formatage, et comme je n'ai pas créé de plugin je ne sais pas où placer le code concernant le formatage du mail et le template. As -tu une idée à me proposer ?

Merci d'avance
Lu

Soumis par Lu (non vérifié) le 06/09/2017 à 10:27 - Permalien

Bonjour ! Merci pour ce billet bien utile, mais il me reste une question.
Je souhaite envoyer automatiquement des mails depuis un module custom en passant par Swiftmailer. J'ai suivi les deux premières étapes que tu proposes et ai installé Swiftmailer. J'ai configuré le mailsystem de mon projet drupal 8 pour que les mails soient envoyés par Swift.

Les mails partent bien, via Swift, mais ils n'ont encore aucun formattage. Or, comme je n'ai pas eu besoin d'installer ou de créer un plugin comme tu l'expliques, je ne sais pas où placer le code de formattage du mail. As -tu une idée de la façon dont je peux lier un template aux mails que j'envoie dans cette situation ?

Merci d'avance,
Lu

Soumis par fabrice le 06/09/2017 à 10:48 - Permalien

Bonjour, Il faut déclarer le template que tu veux utiliser avec hook_theme. Par exemple tu déclares le theme (template) my_email.

Puis dans un hook_mail_alter(), il suffit d'indiquer à swiftmailer d'utiliser ton theme avec cette clé :

$message['params']['theme'] = 'my_email';

Soumis par ludovic (non vérifié) le 28/02/2018 à 11:21 - Permalien

Merci mille fois pour ce tutoriel extrêmement bien fait .

Soumis par Florian drupal (non vérifié) le 05/03/2018 à 14:36 - Permalien

Une petite erreur s'est glissée dans la fonction : template_preprocess_my_module_courriel, il manque un S à
!empty($variables['message']['options']

Soumis par Faber (non vérifié) le 25/06/2018 à 13:40 - Permalien

Bonjour,
Je me casse les dents depuis un certain temps sur ce sujet, et j'ai trouvé ce tutoriel très clair. Mais je bloque sur la fonction cleanBody().
J'ai vu le commentaire plus haut le relevait, et je comprends que vous n'ayez pas tout détaillé dans ce billet, mais pouvez-vous me donner quelques pistes ou explications concernant cette fonction et son rôle dans tout ça ?
Merci d'avance de votre temps, Faber.

Soumis par BDSI (non vérifié) le 16/07/2018 à 19:59 - Permalien

Bonjour,
Merci pour ce tutoriel qui est bien détaillé, juste un petit problème pour moi le texte (body) de l’émail envoyé contient "Bonjour," je crois que le texte de message (body) passe vide au template. Aide s'il vous-plait.

Soumis par Alexandre (non vérifié) le 17/12/2018 à 16:15 - Permalien

Bonjour,
Je viens d'utiliser votre post afin de réaliser mes envoies de mails HTML, mais j'étais confronté au problème suivant :
Error: Call to a member function get() on null in ~/core/lib/Drupal/Core/Mail/Plugin/Mail/PhpMail.php on line 105
J'ai pu le régler grâce à l'ajout du code suivant dans le constructeur de MyModuleMail :
parent::__construct();

Soumis par Karl (non vérifié) le 12/08/2019 à 17:54 - Permalien

Bonjour,
J'ai suivi les étapes une à une et j'ai un petit soucis.

Mon template n'est apparemment pas reconnu. Le mail s'envoi mais le contenu est seulement : 'Your wonderful message about (le nom de mon site)'.

J'ai l'impression que lors de l'étape de formatage, ça ne prend pas en compte le $render pour que Drupal utilise mon template personnalisé ou alors mon plugin n'est pas reconnu. Comment puis je tester ça ? ou avez vous directement la solution ^^ ?

Merci

Cordialement

Soumis par GilbertdeLyon (non vérifié) le 11/05/2022 à 10:42 - Permalien

Merci pour ce tuto bien utile.
j'ai donc codé un module d'envoi de notification par mail à chaque création d'un nouvel article ou commentaire.
En phase de test tout fonctionne, mais avec un petit nombre de destinataires. Pour l'instant une notification = moins d'une dizaine de mails envoyés (via le SMTP de O2switch qui héberge le site).
Je me pose maintenant la question de l'envoi en masse, par exemple pour notifier une centaine de destinataires.
O2switch suggère de ne pas dépasser un quota de 30 mails par minute sous peine d'être considéré comme spammeur. Je ne sais pas si ce nombre est réaliste?
Sinon y a-t-il un moyen simple de gérer l'échelonnement des envois.? (fonction sleep() dans le script php?)

Ajouter un commentaire