Conseils plugin envoi de mail massif

Bonjour,
je suis en train de mettre en place un petit plugin qui servira a envoyer des mails personnalises aux auteurs enregistres d un site.
Le contenu des mails est prealablement généré et stocke en bdd, ensuite la tache d envoi des mails est lancée par un cron. J aurai besoin de conseils :
- puis je lancer l envoi de plusieurs centaines de mails (format html assez lourd) d un coup d un seul ? Je pense, qu il y a une limite de temps d execution pour un script php, celui ci risque d etre insuffisant
- qu elle serait la meilleure technique pour temporiser le postage ?

merci pour tout conseil
cordialement
triton

Bonjour,

Il existe déjà les plugins Ma Lettre :
http://www.spip-contrib.net/Plugin-Ma-lettre
Et SPIP-Listes :
http://www.spip-contrib.net/SPIP-Listes

Ne font-ils pas déjà l’affaire? Si la réponse est non, pourquoi ne pas aider à l’ajout de fonctionnalités à ses plugins?

Cordialement,
Teddy

Le 28 mai 2009 09:46, triton <triton@pointcentral.net> a écrit :

Bonjour,
je suis en train de mettre en place un petit plugin qui servira a envoyer des mails personnalises aux auteurs enregistres d un site.
Le contenu des mails est prealablement généré et stocke en bdd, ensuite la tache d envoi des mails est lancée par un cron. J aurai besoin de conseils :

  • puis je lancer l envoi de plusieurs centaines de mails (format html assez lourd) d un coup d un seul ? Je pense, qu il y a une limite de temps d execution pour un script php, celui ci risque d etre insuffisant
  • qu elle serait la meilleure technique pour temporiser le postage ?

merci pour tout conseil
cordialement
triton


liste spip
spip@rezo.net - désabonnement : spip-off@rezo.net

Infos et archives : http://listes.rezo.net/mailman/listinfo/spip

Documentation de SPIP : http://www.spip.net/

irc://irc.freenode.net/spip ou http://embed.mibbit.com/?server=irc.freenode.net&channel=%23spip

Bonjour,

Sur un système non spip, j'ai du effectuer des mailings de grosse dimension. La seule solution que j'ai pu trouver pour envoyer tous mes mails était de lancer un script depuis un compte système, ce qui me permettait de contourner la limite d'exécution des scripts de manière radicale et surtout de gagner en temps d'exécution. Maintenant ce type de manœuvres ne se justifie que pour l'envoi de mailings vraiment massifs. Malgré tout il me faut tout de même quelques heures pour expédier un peu moins de 100 000 mails.

Une solution à votre problème pourrait donc être d'avoir un script php lancé par les taches cron du système ( et non celles de spip ) qui envoie à fréquence régulière des tranches d'emails générés par le plugin. Le système d'e-commerce Magento par exemple fonctionne selon ce principe pour la gestion des alertes produits et des newsletters.
*/5 * * * * mon-utilisateur /usr/bin/php5 -f /var/www/XXXXX/cron.php

Si votre souci est la fréquence d'exécution des taches cron de spip ( la nuit par exemple ), je suppose qu'il est possible de générer du trafic artificiel sur votre site de manière à assurer l'exécution périodique du script du plugin (en faisant appeler un script via une tache cron du système ou équivalent qui fait tourner l'index du site ).

Dans tous les cas, une solution passant exclusivement par spip est plus propre. Il serait donc instructif de faire tourner une tache cron spip qui ne créé qu'une ligne de log dans un fichier. Dans le style de cette contrib: http://www.spip-contrib.net/Ajouter-une-tache-CRON-dans-un .
De la vous saurez a quoi vous attendre niveau régularité et vous pourrez envisager la manière dont traiter vos taches d'envois: dimensionnement des envois etc.

Sinon, une dernière piste ( dangereuse à mon avis ), c'est de faire un script d'émission qui bricole sur "set_time_limit" :
http://fr3.php.net/manual/fr/function.set-time-limit.php
En cas de boucle infinie, ça peut très mal se passer ...

J'espère que mes divagations auront pu un peu aider ^^

Cordialement,

Vincent

Yoann NOGUES a écrit :

triton a écrit :

Bonjour,
je suis en train de mettre en place un petit plugin qui servira a envoyer des mails personnalises aux auteurs enregistres d un site.
Le contenu des mails est prealablement généré et stocke en bdd, ensuite la tache d envoi des mails est lancée par un cron. J aurai besoin de conseils :
- puis je lancer l envoi de plusieurs centaines de mails (format html assez lourd) d un coup d un seul ? Je pense, qu il y a une limite de temps d execution pour un script php, celui ci risque d etre insuffisant
- qu elle serait la meilleure technique pour temporiser le postage ?

Pourquoi ne pas utiliser spip-listes , dans ton cas ?

sinon pour répondre, faire comme fait spip-listes des envoi par lots ( 10 par 10 , 20 par 20 , etc )

Dans mon cas il ne s agit pas d une news letter (les gens ne sont pas senses s inscrire/desinscrire) mais d un outil permettant a un webmaster d envoyer d office des mails a ses auteurs/visiteurs (des adherents en l occurence). Spip-liste ne semble pas permettre de personnaliser les courriers avec des champs genre : Cher monsier <machin>. La doc semble dire que c est faisable, mais impossible a mettre en place...
Par contre, je ne connaissais pas le plugin Ma_Lettre, mais il ne semble pas convenir non plus...
La fonction que j essaie de mettre en place doit s inserer dans le plugin association, elle permettra d envoyer les courriers de type relance de cotisation, invitation a des evenements... Je n ai pas les competences en developpement necessaire pour essayer d enrichir un plugin tel que spip_listes, beaucoup trop complexe pour moi. J essai donc de faire une petite fonction circonscrite a une tache simple mais le plus proprement possible...
Bien sur, si j arrive a quelque chose de bien, je le proposerai a qui n en veut
Je relis une 12eme fois le message de Vincent sur la bonne pratique des cron, et je reviens des que j ai compris...
merci pour les reponses...
triton

Alors, il semble que le plugin Facteur permet de centraliser les modes d’envoi (passerelle) de ce genre de fonction.

C’est cru comprendre que le sujet était peu houleux sur la zone (ou ailleurs) et je ne cherche pas à faire de la pub mais juste énoncer des possibilités offertes sur la galaxie spipienne.
Si j’ai bien compris, artego met ses plugins en GPL. Et voici la présentation, sur leur site car pas encore dispo sur Contrib :
http://www.artego.fr/-Envoi-de-notifications-

Cela devrait te simplifier la tâche pour les protocoles d’envoi et ainsi te centraliser sur les modes de rendu des champs spécifiques tels que %nom_utlisateur% etc.

Le 28 mai 2009 16:47, triton <triton@pointcentral.net> a écrit :

Yoann NOGUES a écrit :

triton a écrit :

Bonjour,
je suis en train de mettre en place un petit plugin qui servira a envoyer des mails personnalises aux auteurs enregistres d un site.
Le contenu des mails est prealablement généré et stocke en bdd, ensuite la tache d envoi des mails est lancée par un cron. J aurai besoin de conseils :

  • puis je lancer l envoi de plusieurs centaines de mails (format html assez lourd) d un coup d un seul ? Je pense, qu il y a une limite de temps d execution pour un script php, celui ci risque d etre insuffisant
  • qu elle serait la meilleure technique pour temporiser le postage ?

Pourquoi ne pas utiliser spip-listes , dans ton cas ?

sinon pour répondre, faire comme fait spip-listes des envoi par lots ( 10 par 10 , 20 par 20 , etc )

Dans mon cas il ne s agit pas d une news letter (les gens ne sont pas senses s inscrire/desinscrire) mais d un outil permettant a un webmaster d envoyer d office des mails a ses auteurs/visiteurs (des adherents en l occurence). Spip-liste ne semble pas permettre de personnaliser les courriers avec des champs genre : Cher monsier . La doc semble dire que c est faisable, mais impossible a mettre en place…
Par contre, je ne connaissais pas le plugin Ma_Lettre, mais il ne semble pas convenir non plus…
La fonction que j essaie de mettre en place doit s inserer dans le plugin association, elle permettra d envoyer les courriers de type relance de cotisation, invitation a des evenements… Je n ai pas les competences en developpement necessaire pour essayer d enrichir un plugin tel que spip_listes, beaucoup trop complexe pour moi. J essai donc de faire une petite fonction circonscrite a une tache simple mais le plus proprement possible…
Bien sur, si j arrive a quelque chose de bien, je le proposerai a qui n en veut
Je relis une 12eme fois le message de Vincent sur la bonne pratique des cron, et je reviens des que j ai compris…
merci pour les reponses…

triton


liste spip
spip@rezo.net - désabonnement : spip-off@rezo.net

Infos et archives : http://listes.rezo.net/mailman/listinfo/spip

Documentation de SPIP : http://www.spip.net/

irc://irc.freenode.net/spip ou http://embed.mibbit.com/?server=irc.freenode.net&channel=%23spip

Dans mon cas il ne s agit pas d une news letter (les gens ne sont pas senses s inscrire/desinscrire) mais d un outil permettant a un webmaster d envoyer d office des mails a ses auteurs/visiteurs (des adherents en l occurence). Spip-liste ne semble pas permettre de personnaliser les courriers avec des champs genre : Cher monsier . La doc semble dire que c est faisable, mais impossible a mettre en place…
Par contre, je ne connaissais pas le plugin Ma_Lettre, mais il ne semble pas convenir non plus…
La fonction que j essaie de mettre en place doit s inserer dans le plugin association, elle permettra d envoyer les courriers de type relance de cotisation, invitation a des evenements… Je n ai pas les competences en developpement necessaire pour essayer d enrichir un plugin tel que spip_listes, beaucoup trop complexe pour moi. J essai donc de faire une petite fonction circonscrite a une tache simple mais le plus proprement possible…
Bien sur, si j arrive a quelque chose de bien, je le proposerai a qui n en veut

Si j’ai bien compris, la quantité de mails générés sera relativement faible, de l’ordre de quelques centaines par envois ? Si c’est le cas, et qu’il y a un minimum de trafic sur le site ( la nuit en particulier ) je pense qu’il n’est pas nécessaire de se casser la tête avec des scripts cron lancés par le système d’exploitation.

Je relis une 12eme fois le message de Vincent sur la bonne pratique des cron, et je reviens des que j ai compris…
merci pour les reponses…

Oulah, on dirait que je suis toujours aussi clair … Je donnais juste quelques pistes ( assez vagues, j’en conviens ! ) que j’ai pu suivre après avoir été confronté à des problèmes similaires.
Ceci dit, le plugin Lettre d’information d’artego proposé par Teddy Payet pourrait en partie répondre à votre problème. Je l’ai testé sur du spip 1.9 et il me semble qu’il offrait des fonctionnalités du type « Cher monsier  ».
Le seul souci serait la gestion des abonnements des personnes ( mais de mémoire, il accepte les imports et exports CSV, ce qui peut permettre de tricher ! ).

Cordialement,

Vincent

Oulah, on dirait que je suis toujours aussi clair ... Je donnais juste quelques pistes ( assez vagues, j'en conviens ! ) que j'ai pu suivre après avoir été confronté à des problèmes similaires.

Non, non ! c est moi, j' ai du mal avec ces concepts qui me sont un peu etrangers (a la base je suis peintre quand meme...)

Ceci dit, le plugin Lettre d'information d'artego proposé par Teddy Payet pourrait en partie répondre à votre problème. Je l'ai testé sur du spip 1.9 et il me semble qu'il offrait des fonctionnalités du type "Cher monsier <machin>".

Ah, mais ca, ca y est j y suis parvenu proprement grace a un modele qui recupere dynamiquement le contexte et qui boucle sur auteurs_elargis, je peux donc faire un cher monsieur <machin> ne le <datenaissance> vous devez vous acquitter de la la somme de <cotisation> (et ce grace a une syntaxe particulierement exotique propose sur cette liste)

Le seul souci serait la gestion des abonnements des personnes ( mais de mémoire, il accepte les imports et exports CSV, ce qui peut permettre de tricher ! ).

Ca, le plugin association permet de gerer.
Et j ai bien compris ton explication sur les crons. La question que je me posai, mais je crois avoir maintenant la reponse, c est :
est ce que c est ma fonction d envoi de mail qui doit temporiser les envois, avec genre un sleep ou autre comme tu l evoques (temporiser les envois avec un sleep... n importe quoi les images mentales qu evoque spontanément cette phrase...)
ou alors, ma fonction doit etre configuree pour envoyer genre 10 mails, et etre appelee 60 fois par le cron (j ai 600 personnes dans la bdd). A chaque fois qu un mail est envoye, je pose un flag sur l enregistrement pour signaler a la fonction que ce mail est deja poste.

Je pense que la solution est la deux (le cron appele 60 fois la fonction toute les 5 mn par exemple)
Par contre, si j ai bien compris le principe du cron spip, il permet juste de dire : execute cette fonction toute les xx secondes, mais je ne vois pas comment faire pour lui dire execute cette fonction toutes les xx secondes a partir de 22h ce soir ?
merci pour les conseils
triton

Cordialement,

Vincent

--
---- Christophe Ségura -------
---- PointCentral ------------
---- La mare aux Tritons -----
---- 31460 Vendine -----------
-- Tel/Fax : 05 61 20 69 37 --

Ca, le plugin association permet de gerer.
Et j ai bien compris ton explication sur les crons. La question que je me posai, mais je crois avoir maintenant la reponse, c est :
est ce que c est ma fonction d envoi de mail qui doit temporiser les envois, avec genre un sleep ou autre comme tu l evoques (temporiser les envois avec un sleep... n importe quoi les images mentales qu evoque spontanément cette phrase...)
ou alors, ma fonction doit etre configuree pour envoyer genre 10 mails, et etre appelee 60 fois par le cron (j ai 600 personnes dans la bdd). A chaque fois qu un mail est envoye, je pose un flag sur l enregistrement pour signaler a la fonction que ce mail est deja poste.
Je pense que la solution est la deux (le cron appele 60 fois la fonction toute les 5 mn par exemple)
Par contre, si j ai bien compris le principe du cron spip, il permet juste de dire : execute cette fonction toute les xx secondes, mais je ne vois pas comment faire pour lui dire execute cette fonction toutes les xx secondes a partir de 22h ce soir ?
merci pour les conseils
triton

Effectivement, c'est l'idée ! En fait, il faut voir la partie exécutée par les taches cron comme totalement indépendante du reste, avec au milieu la base de donnée comme pont entre le plugin et sa tache cron.
Si on se base sur un modèle dans ce goût, l'envoi d'email se passe comme ceci :

ponctuellement )) action de l'utilisateur -> Création des emails à envoyer ( en base ou en base + fichiers, ou simplement stockage des informations nécessaires a leur création plus tard ) et stockage dans une table de la base.
Cette étape équivaut à la création d'une file d'envoi sur un systèmes de mails.

périodiquement )) la tache cron spip est exécutée ( toutes les 5 minutes par exemple ).
    - si il est moins de 22h, elle ne fait rien et rend la main.
    - si il est plus de 22h, elle regarde si la file contient des mails à envoyer et l'état du sémaphore (variable booléenne témoin ) d'envoi.
       S'il y a des messages en queue et que le sémaphore est libre, elle place le sémaphore à vrai et envoie une tranche de mails ( type 10 messages ).
    - à la fin de l'exécution, elle libère le sémaphore.

Le sémaphore est juste un artifice pour éviter que cette fonction soit lancée deux fois en parallèle et éviter ainsi de surcharger le système en cas de réglage trop court du délais d'exécution de la tache.

Vincent a écrit :

Ca, le plugin association permet de gerer.
Et j ai bien compris ton explication sur les crons. La question que je me posai, mais je crois avoir maintenant la reponse, c est :
est ce que c est ma fonction d envoi de mail qui doit temporiser les envois, avec genre un sleep ou autre comme tu l evoques (temporiser les envois avec un sleep... n importe quoi les images mentales qu evoque spontanément cette phrase...)
ou alors, ma fonction doit etre configuree pour envoyer genre 10 mails, et etre appelee 60 fois par le cron (j ai 600 personnes dans la bdd). A chaque fois qu un mail est envoye, je pose un flag sur l enregistrement pour signaler a la fonction que ce mail est deja poste.
Je pense que la solution est la deux (le cron appele 60 fois la fonction toute les 5 mn par exemple)
Par contre, si j ai bien compris le principe du cron spip, il permet juste de dire : execute cette fonction toute les xx secondes, mais je ne vois pas comment faire pour lui dire execute cette fonction toutes les xx secondes a partir de 22h ce soir ?
merci pour les conseils
triton

Effectivement, c'est l'idée ! En fait, il faut voir la partie exécutée par les taches cron comme totalement indépendante du reste, avec au milieu la base de donnée comme pont entre le plugin et sa tache cron.
Si on se base sur un modèle dans ce goût, l'envoi d'email se passe comme ceci :

ponctuellement )) action de l'utilisateur -> Création des emails à envoyer ( en base ou en base + fichiers, ou simplement stockage des informations nécessaires a leur création plus tard ) et stockage dans une table de la base.
Cette étape équivaut à la création d'une file d'envoi sur un systèmes de mails.

périodiquement )) la tache cron spip est exécutée ( toutes les 5 minutes par exemple ).
   - si il est moins de 22h, elle ne fait rien et rend la main.
   - si il est plus de 22h, elle regarde si la file contient des mails à envoyer et l'état du sémaphore (variable booléenne témoin ) d'envoi.
      S'il y a des messages en queue et que le sémaphore est libre, elle place le sémaphore à vrai et envoie une tranche de mails ( type 10 messages ).
   - à la fin de l'exécution, elle libère le sémaphore.

Le sémaphore est juste un artifice pour éviter que cette fonction soit lancée deux fois en parallèle et éviter ainsi de surcharger le système en cas de réglage trop court du délais d'exécution de la tache.

J a i tout compris !
Je vais mettre ca en place, je n en suis pas tres loin...
Sinon, pour ma comprehension, ne serait il pas possible de creer la tache cron sur l action de l utilisateur qui cree le publipostage, et supprimer la tache cron une fois tous les mails postes ?
de maniere a ne pas avoir une tache cron qui tourne en permanence et balance une requete (meme minime) sur la bdd ?
merci beaucoup pour cette explication tres clair, ca me permet d y voir vraiment plus clair.
cordialement
triton

J a i tout compris !
Je vais mettre ca en place, je n en suis pas tres loin...
Sinon, pour ma comprehension, ne serait il pas possible de creer la tache cron sur l action de l utilisateur qui cree le publipostage, et supprimer la tache cron une fois tous les mails postes ?
de maniere a ne pas avoir une tache cron qui tourne en permanence et balance une requete (meme minime) sur la bdd ?
merci beaucoup pour cette explication tres clair, ca me permet d y voir vraiment plus clair.
cordialement
triton

Ravi d'avoir pu aider ! Concernant la possibilité de désactiver la tache cron, je ne pense pas que ce soit faisable dans la mesure ou elle est créée à l'installation du plugin, et supprimée à sa désactivation.
Vu le nombre de requêtes faites sur la base lors de la construction d'une page ( hors cache ), ce n'est pas franchement significatif ( surtout si la requête est prévue pour limiter la casse: http://doc.spip.org/@sql_countsel ).
J'aurais donc tendance à ne pas trop me soucier de ce point.

Ceci dit, il est possible de d'inhiber la fonction d'émission des mails via un nouveau sémaphore.
Si il est placé dans les variables d'environnement, cela doit permettre de faire cela élégamment dans le sens ou elles sont déjà chargées par spip :
pour le consulter : $semaphore_envoi = $GLOBALS['meta']['mon_plugin_semaphore_envoi'];
Pour créer / supprimer :
ecrire_meta('mon_plugin_semaphore_envoi',$valeur,'non');
effacer_meta('mon_plugin_semaphore_envoi');
Sinon, encore plus violent: utiliser un fichier en guise de sémaphore ( mais gare aux problèmes de droits d'écriture, voir de sécurité ).

Dans tous les cas, ce sémaphore doit être placé à vrai par la fonction utilisateur, et à faux par la fonction lancée par cron quand il n'y a plus de mails à envoyer en file.