From 3ff197b51a0ee8a4ac09eedc7af71b206d876d20 Mon Sep 17 00:00:00 2001
From: efalcy <efalcy@afi-sa.fr>
Date: Tue, 9 Jun 2015 17:43:59 +0200
Subject: [PATCH] dev #14064 : newsletter , send one mail instead of bcc and
 add unsubscribe link

---
 library/Class/Batch/SendNewsletters.php       | 26 +++++----
 library/Class/Newsletter.php                  | 54 +++++++++++++++++-
 tests/library/Class/NewsletterMailingTest.php | 56 +++++++++++++------
 3 files changed, 105 insertions(+), 31 deletions(-)

diff --git a/library/Class/Batch/SendNewsletters.php b/library/Class/Batch/SendNewsletters.php
index 21dc9d5aa0c..14bdc2a91f7 100644
--- a/library/Class/Batch/SendNewsletters.php
+++ b/library/Class/Batch/SendNewsletters.php
@@ -25,7 +25,8 @@ class Class_Batch_SendNewsletters extends Class_Batch_Abstract {
 	protected
 		$_newsletter,
 		$_previous_mail,
-		$_time_limit;
+		$_time_limit,
+		$_template_mail;
 
 
 	public function __construct($newsletter) {
@@ -69,6 +70,8 @@ class Class_Batch_SendNewsletters extends Class_Batch_Abstract {
 		Class_NewsletterSubscription::resetSendFlagForNewsletter($letter->getId());
 
 		$this->_previous_mail = '';
+		$this->_template_mail=$letter->newTemplate();
+		xdebug_break();
 		while (0 < count(array_filter($receivers = $letter->getReceivers($page_size)))) {
 			$this->_clearMemory()
 					 ->_giveMeMoreTime(30)
@@ -76,7 +79,7 @@ class Class_Batch_SendNewsletters extends Class_Batch_Abstract {
 
 			$letter->setLastDistributionDateWithFormat();
 			Class_NewsletterSubscription::updateSendFlagForReceivers($letter->getId(),
-																															 $letter->getReceivers($page_size));
+																															 $receivers);
 		}
 
 		$this->getTimeLimit()->reset();
@@ -100,23 +103,24 @@ class Class_Batch_SendNewsletters extends Class_Batch_Abstract {
 
 
 	protected function _sendPage($receivers) {
-		$letter = $this->_newsletter;
-
-		$mail = $letter->newMail();
-		$mail->addTo($letter->getExpediteur());
 
-		foreach($receivers as $receiver)
-			$this->_addReceiverTo($receiver, $mail);
+		foreach($receivers as $receiver) {
+			$letter = $this->_newsletter;
+			$mail = $letter->newMailFromTemplate($this->_template_mail,$receiver);
+			$this->_sendTo($receiver,$mail);
 
-		$mail->send();
+		}
 	}
 
 
-	protected function _addReceiverTo($receiver, $mail) {
+	protected function _sendTo($receiver,$mail) {
 		$receiver_mail = $receiver->getMail();
 		if ($this->_previous_mail != $receiver_mail) {
-			$mail->addBcc($receiver_mail);
 			$this->_previous_mail = $receiver_mail;
+			$mail->addTo($receiver_mail);
+
+			if (count($mail->getRecipients())>0)
+				$mail->send();
 		}
 	}
 
diff --git a/library/Class/Newsletter.php b/library/Class/Newsletter.php
index 4ed1a48102c..2c1ac3f186b 100644
--- a/library/Class/Newsletter.php
+++ b/library/Class/Newsletter.php
@@ -85,7 +85,8 @@ class Class_Newsletter extends Storm_Model_Abstract {
 	public function sendTo($destinataire) {
 		$mail = $this->newMail();
 		$mail->addTo($destinataire);
-		$mail->send();
+		if (count($mail->getRecipients())>0)
+			$mail->send();
 	}
 
 
@@ -97,6 +98,37 @@ class Class_Newsletter extends Storm_Model_Abstract {
 	}
 
 
+	public function fillTemplate($user,$body) {
+		return str_replace("%user.id%",$user->getId(),$body);
+	}
+
+
+	public function newMailFromTemplate($template,$user) {
+		$mail = new ZendAfi_Mail('utf8');
+		xdebug_break();
+		$mail
+			->setSubject($template->getTitre())
+			->setBodyText($this->fillTemplate($user,$template->getBodyText(true)))
+			->setBodyHTML($this->fillTemplate($user,$template->getBodyHTML(true)))
+			->setFrom($template->getExpediteur());
+		return $mail;
+	}
+
+
+
+	public function newTemplate() {
+		$template=new Class_Newsletter();
+		$notices = $this->getNotices();
+
+		$template
+			->setTitre($this->getTitre())
+			->setBodyText($this->_getBodyText($notices))
+			->setBodyHTML($this->_getBodyHTML($notices))
+			->setExpediteur($this->getExpediteur());
+		return $template;
+	}
+
+
 	public function newMail() {
 		$notices = $this->getNotices();
 
@@ -106,6 +138,7 @@ class Class_Newsletter extends Storm_Model_Abstract {
 			->setBodyText($this->_getBodyText($notices))
 			->setBodyHTML($this->_getBodyHTML($notices))
 			->setFrom($this->getExpediteur());
+
 		return $mail;
 	}
 
@@ -173,12 +206,26 @@ class Class_Newsletter extends Storm_Model_Abstract {
 
 
 
+	public function getUnsubscribeUrl() {
+		return 'http://'.$_SERVER['SERVER_NAME'].BASE_URL.'/newsletter/unsubscribe/newsletter/'.$this->getId().'/user/%user.id%';
+	}
+
+
+	protected function _getUnsubscribeText() {
+		return "Pour se désinscrire à cette newsletter:". $this->getUnsubscribeUrl();
+	}
+
+	protected function _getUnsubscribeHTML() {
+		return '<a href="'.$this->getUnsubscribeUrl().'">Je ne veux plus recevoir cette newsletter</a>';
+	}
+
+
 	protected function _getBodyText($notices) {
 		$lines = array($this->_htmlToText($this->getContenu()));
 
 		foreach($notices as $notice) {
 			$url_notice = sprintf('http://%s/recherche/viewnotice/id/%d',
-                            $_SERVER['SERVER_NAME'].BASE_URL,
+                             $_SERVER['SERVER_NAME'].BASE_URL,
 														$notice->getId());
 
 			$lines []= '- '.$this->_getTitleForNotice($notice);
@@ -188,6 +235,7 @@ class Class_Newsletter extends Storm_Model_Abstract {
 
 		}
 
+		$lines[]=$this->_getUnsubscribeText();
 		return implode("\n", $lines);
 	}
 
@@ -232,7 +280,7 @@ class Class_Newsletter extends Storm_Model_Abstract {
 				'<div style="clear:both"></div>'.
 				'</div>';
 		}
-
+		$html.=$this->_getUnsubscribeHTML();
 		return $html;
 
 	}
diff --git a/tests/library/Class/NewsletterMailingTest.php b/tests/library/Class/NewsletterMailingTest.php
index bd68b5f6feb..c6b4358fbba 100644
--- a/tests/library/Class/NewsletterMailingTest.php
+++ b/tests/library/Class/NewsletterMailingTest.php
@@ -148,7 +148,8 @@ abstract class NewsletterMailingTestCase extends ModelTestCase {
 
 		$this->animations->generateMails(20);
 
-		$this->mail = $this->mock_transport->sent_mail;
+		$this->mails = $this->mock_transport->getSentMails();
+
 	}
 
 
@@ -169,12 +170,12 @@ abstract class NewsletterMailingTestCase extends ModelTestCase {
 
 
 	protected function assertBodyHTMLContains($needle) {
-		$this->assertMIMEPartContains($needle, $this->mail->getBodyHTML());
+		$this->assertMIMEPartContains($needle, $this->mails[0]->getBodyHTML());
 	}
 
 
 	protected function assertBodyTextContains($needle) {
-		$this->assertMIMEPartContains($needle, $this->mail->getBodyText());
+		$this->assertMIMEPartContains($needle, $this->mails[0]->getBodyText());
 	}
 }
 
@@ -203,50 +204,71 @@ class NewsletterMailingAnimationsSendMailTest extends NewsletterMailingTestCase
 
 	/** @test */
 	public function mailShouldBeSendFromPortalAdmin() {
-		$this->assertContains('flo@afi-sa.fr', $this->mail->getFrom());
+		$this->assertContains('flo@afi-sa.fr', $this->mails[0]->getFrom());
 	}
 
 
 	/** @test */
 	public function subjectShouldBeAnimationsDuMois() {
-		$this->assertEquals('Animations du mois', $this->mail->getSubject());
+		$this->assertEquals('Animations du mois', $this->mails[0]->getSubject());
+	}
+
+
+
+	/** @test */
+	public function bodyTextShouldContainsUnsubscribeLinks() {
+		$this->assertContains('/newsletter/unsubscribe/newsletter/1/user/2',
+													$this->mails[1]->getBodyText(true));
+
+	}
+
+
+	/** @test */
+	public function bodyHTMLShouldContainsUnsubscribeLinks() {
+		$this->assertContains('/unsubscribe/newsletter/1/user/2',
+													$this->mails[1]->getBodyHTML(true));
+
 	}
 
 
 	/** @test */
 	public function bodyTextShouldBeDecouverteCuisineDuMonde() {
 		$this->assertContains('Découverte des cuisines du monde',
-													quoted_printable_decode($this->mail->getBodyText()->getContent()));
+													quoted_printable_decode($this->mails[0]->getBodyText()->getContent()));
 	}
 
 
 	/** @test */
-	public function bccShouldContainsRduboisAtFreeDotFr() {
-		$this->assertContains('rdubois@afi-sa.fr', implode(',',$this->mail->getRecipients()));
+	public function mailShouldContainsRduboisAtFreeDotFr() {
+		$this->assertContains('rdubois@afi-sa.fr', implode(',',$this->mails[0]->getRecipients()));
 	}
 
 
 	/** @test */
-	public function bccShouldContainsMduchampAtHotmailDotCom() {
-		$this->assertContains('mduchamp@afi-sa.fr', $this->mail->getRecipients());
+	public function mailShouldContainsMduchampAtHotmailDotCom() {
+		$this->assertContains('mduchamp@afi-sa.fr', $this->mails[1]->getRecipients());
 	}
 
 
 	/** @test */
-	public function bccShouldNotContainsZork() {
-		$this->assertNotContains('zork', $this->mail->getRecipients());
+	public function ShouldNotContainsZork() {
+		$this->assertNotContains('zork', $this->mails[0]->getRecipients());
 	}
 
 
 	/** @test */
-	public function recipientsShouldContainsPortalAdmin() {
-		$this->assertContains('flo@afi-sa.fr', $this->mail->getRecipients());
+	public function recipientsShouldContainsPcortalAdmin() {
+		$this->assertContains('flo@afi-sa.fr', $this->mails[0]->getRecipients());
 	}
 
+	/** @test */
+	public function twoMailShouldBeSent() {
+		$this->assertCount(2,$this->mails);
+	}
 
 	/** @test */
-	public function mailShouldHave3Recipients() {
-		$this->assertEquals(3, count($this->mail->getRecipients()));
+	public function mailShouldHave1Recipient() {
+		$this->assertEquals(1, count($this->mails[0]->getRecipients()));
 	}
 
 
@@ -441,7 +463,7 @@ class NewsletterMailingDedupTest extends ModelTestCase {
 	protected function assertProcyonNotDuplicatedIn($mails) {
 		$sent = 0;
 		foreach ($mails as $mail)
-			foreach ($mail->getHeaders()['Bcc'] as $recipient)
+			foreach ($mail->getHeaders()['To'] as $recipient)
 				if ('<procyon@centre-de-recherche.fr>' === $recipient)
 					$sent++;
 
-- 
GitLab