Is there a way to remove the return-path that kohana is setting in emails? - email

Our site uses Kohana and php and we are using sendgrid to send transactional emails. With gmail we're having a ton of spam issues and we only send opt-in emails and have a high open rate. One of the potential issues is that our emails seem to have TWO return-paths in the header:
Is being set by us in Kohana
is being inserted by sendgrid.
Sendgrid says that when they send a message, they take over that 'envelope from' for the sake of handling Bounce management. But we can't figure out a way to have Kohana not insert this. Any suggestions? CODE EXAMPLE:
Kohana uses Swift to send mails. How we send them now is below. We've tried removing reply-to via
$message->headers->set('reply-to', '');
but it doesn't appear to work. Funny enough, setting it to a non-empty value alters it, but there doesn't seem to be a way to get rid of it altogether.
Full code for this function:
/**
* Send an email message.
*
* #param string|array recipient email (and name), or an array of To, Cc, Bcc names
* #param string|array sender email (and name)
* #param string message subject
* #param string message body
* #param boolean send email as HTML
* #param string Reply To address. Optional, default null, which defaults to From address
* #return integer number of emails sent
*/
public static function send($category, $to, $from, $subject, $message, $html = FALSE, $replyto = null)
{
// Connect to SwiftMailer
(email::$mail === NULL) and email::connect();
// Determine the message type
$html = ($html === TRUE) ? 'text/html' : 'text/plain';
// Append mixpanel tracking pixel to html emails
if ($html) {
$mixpanel_token = FD_DEV_MODE ? "08c59f4e26aa718a1038459af75aa559" : "d863dc1a3a6242dceee1435c0a50e5b7";
$json_array = '{ "event": "e-mail opened", "properties": { "distinct_id": "' . $to . '", "token": "' . $mixpanel_token . '", "time": ' . time() . ', "campaign": "' . $category . '"}}';
$message .= '<img src="http://api.mixpanel.com/track/?data=' . base64_encode($json_array) . '&ip=1&img=1"></img>';
}
// Create the message
$message = new Swift_Message($subject, $message, $html, '8bit', 'utf-8');
// Adding header for SendGrid, added by David Murray
$message->headers->set('X-SMTPAPI', '{"category" : "' . $category . '"}');
if (is_string($to))
{
// Single recipient
$recipients = new Swift_Address($to);
}
elseif (is_array($to))
{
if (isset($to[0]) AND isset($to[1]))
{
// Create To: address set
$to = array('to' => $to);
}
// Create a list of recipients
$recipients = new Swift_RecipientList;
foreach ($to as $method => $set)
{
if ( ! in_array($method, array('to', 'cc', 'bcc')))
{
// Use To: by default
$method = 'to';
}
// Create method name
$method = 'add'.ucfirst($method);
if (is_array($set))
{
// Add a recipient with name
$recipients->$method($set[0], $set[1]);
}
else
{
// Add a recipient without name
$recipients->$method($set);
}
}
}
if (is_string($from))
{
// From without a name
$from = new Swift_Address($from);
}
elseif (is_array($from))
{
// From with a name
$from = new Swift_Address($from[0], $from[1]);
}
// Reply To support, not standard in Swift, added by Soham
if (!$replyto) $replyto = $from;
$message->setReplyTo($replyto);
return email::$mail->send($message, $recipients, $from);
}

This is not really a Kohana question but more of a Swiftmailer question, since Swiftmailer comes not standard with the Kohana Framework. According to the Swiftmailer docs you can set/get the Return-Path explicitly:
$message->setReturnPath('bounces#address.tld');
Hopes this helps!

i just wanna say thank you for providing this solution for me, indirectly..
// Adding header for SendGrid, added by David Murray
$message->headers->set('X-SMTPAPI', '{"category" : "INSERT CATEGORY HERE"}');
X-SMTPAPI usage documentation from Sendgrid's Website is sucks..

Related

Creating an attachment for MailMessage

From my extbase 6.2 extension I want to send different e-mails.
In a controller class I wrote a mail function that looks like this:
(notice no #param for $attachment - see my question at the end)
/**
*
* #param string $to
* #param string $subject
* #param string $email_prefix
* #param string $msg
* #param string $email_suffix
*/
public function mailAction($to, $subject, $email_prefix, $msg, $email_suffix, $attachment = null) {
try {
$from = \TYPO3\CMS\Core\Utility\MailUtility::getSystemFrom();
$body = $email_prefix
. PHP_EOL . PHP_EOL
. $msg
. PHP_EOL . PHP_EOL
. $email_suffix;
$htmlBody = nl2br($body);
$toEmail = $to;
$mail = \TYPO3\CMS\Core\Utility\GeneralUtility::makeInstance('TYPO3\\CMS\\Core\\Mail\\MailMessage');
$mail->setFrom($from)
->setTo(array($toEmail))
->setSubject($subject)
->setBody($htmlBody, 'text/html');
$mail->addPart($body, 'text/plain');
if ($attachment) {
$mail->attach($attachment);
}
if (empty($toEmail) || strpos($toEmail, '#') === FALSE) {
$this->addFlashMessage('Die Mail konnte nicht verschickt werden! Keine Email-Adresse des Empfängers', '', \TYPO3\CMS\Core\Messaging\FlashMessage::ERROR
);
} else {
if ($mail->send()) {
$this->addFlashMessage('Die Mail für wurde verschickt!', '');
} else {
$this->addFlashMessage('Die Mail konnte nicht verschickt werden!', '', \TYPO3\CMS\Core\Messaging\FlashMessage::ERROR
);
}
}
$this->redirect('list');
} catch (Exception $e) {
echo 'Caught exception: ', $e->getMessage(), "\n";
}
}
In a function that calls the mail function I tried creating an attachment like this but it failed saying: Fatal error: Class 'Swift_Attachment' not found in.../...Controller.php
$attachment = \Swift_Attachment::newInstance()
->setFilename('Termine.html')
->setContentType('text/html')
->setBody($emailView->render());
Then I call the mail function like this:
$this->redirect('mail', null, null, array(
$to,
$subject,
$email_prefix,
$msg,
$email_suffix,
$attachment));
My questions:
How can I successfully create an object of type Swift_Attachment in a controller of my extbase extension (without creating a MailMessage object beforehand and creating the attachment inside of it)?
What should I put after #param as the type of my $attachment variable in my mail function for this to work?
-- EDIT --
Ok, so apparently no one does that because it's not meant to be.
I now used Rene's approach combining it with Dimitri's scalable answer for multiple attachments. My #param is now array because I have to create the actual attachment after instantiating MailMessage - thanks!
In my extension for 6.2.25 ist works without any including:
$email->attach(\Swift_Attachment::newInstance(
$emailView->render(),
'Termine.html',
'text/html'
));
So you should check why your autoload of classes don't work. Have you tried to clear the cache complete?
To your second question: the correct param declaration should be:
#param \Swift_Mime_Attachment $attachment
But I wouldn't make an redirect, but an $this->forward. You don't need an redirection on client side for this. If this action is only called by an other action I also recommend to make it an protected function an call it directly from your action:
$this->sendMail($to, $subject, $email_prefix, $msg, $email_suffix, $attachment)
-- EDIT --
I recommend to use bypass the attachment information to the function to create the attachment object after the SwitftMailer was initialized:
/**
*
* #param string $to
* #param string $subject
* #param string $email_prefix
* #param string $msg
* #param string $email_suffix
* #param array $attachment
*/
public function mailAction($to, $subject, $email_prefix, $msg, $email_suffix, $attachment = null) {
...
if (is_array($attachment) && array_key_exist('content', $attachment) && array_key_exist('filename', $attachment) && array_key_exist('mime', $attachment)) {
$mail->attach(\Swift_Attachment::newInstance($attachment['content'], $attachment['filename'], $attachment['mime']));
}
...
}
In \TYPO3\CMS\Core\Mail\MailMessage there is a require_once for the swiftmailer classes; they don't seem to be autoloaded. Maybe you can pass the attachment as rendered HTML and create the Swift_Attachment object after instantiating the MailMessage object?
If the solution in 1. works it would be a simple string.
As already stated by Jigal van Hemert you can only create the attachment objects after you create the MailMessage object because the class is not autoloaded. I would just pass the attachment as a filepath to your mail function and it should be handled there and not outside.
if ($attachment) {
$email->attach(\Swift_Attachment::fromPath($attachment));
}
In my opinion it makes more sense if you can pass multiple files instead of one, so the $attachment should be an $attachments array
if(count($attachments)) {
foreach ($attachments as $name => $file) {
if(file_exists($file)) {
if(trim($name) && !is_numeric($name)) {
$email->attach(\Swift_Attachment::fromPath($file)->setFilename($name));
} else {
$email->attach(\Swift_Attachment::fromPath($file));
}
}
}
}

Laravel - How to send email to all users

Im struggling to make a code that sends email to my subscribed users. I want to pass body to view according to users default language, can anyone help me ?
My code:
if($newsletter->save())
{
//get users to send to
$users = User::where('newsletter', '=', '1')->Where('activated', '=', '1')->get();
//Send to all users subscribed
foreach($users as $user)
{
//set info according to user default lang
if($user->default_lang == 'pt')
{
$body = $newsletter_pt;
$subject = Input::get('subject_PT');
}
elseif($user->default_lang == 'de')
{
$body = $newsletter_de;
Input::get('subject_DE');
}
$data = array(
'body' => $body,
'subject' => $subject
);
$from_name = Input::get('from_name');
$from_email = Input::get('from_email');
//QUEUE The Newsletters to send
Mail::queue('admin.newsletters.template1', $data, function($message) use ($user, $subject, $from_name, $from_email)
{
$message->from($from_email, $from_name);
$message->bcc($user->email, $user->name);
$message->subject($subject);
});
} //end foreach
return Redirect::To('admin/newsletters')->with('message', array("1" => "Newsletter enviada com sucesso !"));
}
Thanks a lot ;)
Ensure that the $data array has the information you expect to pass into the view before you call Mail::queue(). It should pass both a $body and $subject variable to your view.
You might also try using Mail::send() instead of Mail::queue() and see if it makes a difference (if you're not using a queueing system). Sometimes the queue() method can trip up when serializing Eloquent models, so if $newsletter_pt or $newsletter_de are Eloquent models they might not make it to the view intact.

Bulk email in cakephp using sendgrid

I am using cakePHP to send smtp email with sendgrid. I would like to be able to execute a single send() to multiple recipients and allow sendgrid to use the vars to replace -name- with the names from a array.
In my cakephp controller method I am testing:
protected function fwtEmail() {
$config = 'sendGrid';
$subject = "test";
$Email = new CakeEmail('sendGrid');
$names = array('user#domain.com'=>'John','user2#domain' =>'Paul');
$Email->To($names);
$vars = array('Paul', 'John');
$Email->viewVars(array('name' => $vars));
$Email->from( array('admin#testdomain.com' => 'Jim') );
$Email->subject($subject);
$template = 'bulk';
$Email->template($template, 'default');
$Email->sendAs = 'both';
return $Email->send();
}
Here is a post on the SendGrid blog that does what you describe.
edit: apologies, this appears not to work in the latest cakephp. I'm trying to find a solution for you.

how do i send an email through joomla

I have a system so folks can register for a class through my Joomla site (I believe it's 3.0). But from there, I would like to send folks an email filling variables from the registration. So something like:
Dear (name), thank you for registering for (class).
This is to remind you your class is tomorrow, (date), at (place).
I believe for the registration, the system uses authorize.net
How can I accomplish this?
Thanks for the help!!
You can use JFactory:getMailer like suggested in the following post. I'm copying here his code example (modified it a bit):
$subject = "Here is the subject of your message.";
$body = "Here is the body of your message.";
$user = JFactory::getUser();
$to = $user->email;
$from = array("me#mydomain.com", "Brian Edgerton");
# Invoke JMail Class
$mailer = JFactory::getMailer();
# Set sender array so that my name will show up neatly in your inbox
$mailer->setSender($from);
# Add a recipient -- this can be a single address (string) or an array of addresses
$mailer->addRecipient($to);
$mailer->setSubject($subject);
$mailer->setBody($body);
# If you would like to send as HTML, include this line; otherwise, leave it out
$mailer->isHTML();
# Send once you have set all of your options
$mailer->send();
That's all there is to it for sending a simple email. If you would like to add carbon copy recipients, include the following before sending the email:
# Add a blind carbon copy
$mailer->addBCC("blindcopy#yourdomain.com");
Another alternative is using JMail::sendMail: http://docs.joomla.org/API17:JMail::sendMail
Fetch the Mail Object:
`$mailer = JFactory::getMailer();`
Set a Sender
$user = JFactory::getUser();
$recipient = $user->email;
$mailer->addRecipient($recipient);
$mailer->setSender($sender);
Recipient
$user = JFactory::getUser();
$recipient = $user->email;
$mailer->addRecipient($recipient);
Create the Mail
$body = 'Body Text';
$mailer->isHtml(true);
$mailer->Encoding = 'base64';
$mailer->setBody($body);
Sending the Mail
$send = $mailer->Send();
if ( $send !== true ) {
echo 'Error sending email: ';
} else {
echo 'Mail sent';
}
https://docs.joomla.org/Sending_email_from_extensions

Get email from Drupal CCK field and send mail using drupal_mail

Hi I'm using the Jobsearch module to build a recruitment site in Drupal 6. By default it sends applications to the email address of the user who posted the job. My problem is all jobs will be posted by a site admin - I need the applications to be sent to BOTH this admin and an email address specified in a CCK field (it's a CCK Email field to be precise).
Trying to extract the CCK field's value and use it in addition to the job poster's (admin's) email and send using drupal_mail but failing - email not sent to the custom CCK email field.
This is what I have attempted (and permutations of), from the Jobsearch module job.module file:
/**
* Implementation of hook_mail().
*/
function job_mail($key, &$message, $params) {
$result = theme('job_mail', $params['job_node'], $params['job_user'], $params['resume_node'], $params['resume_user']);
$message['subject'] = $result['subject'];
$message['body'] = $result['body'];
}
function job_send_email($job_nid, $resume_nid) {
global $user;
$params['job_node'] = $job_node = node_load(array('nid' => $job_nid));
$params['job_user'] = $job_user = user_load(array('uid' => $job_node->uid));
$params['resume_node'] = $resume_node = node_load(array('nid' => $resume_nid));
$params['resume_user'] = $resume_user = user_load(array('uid' => $resume_node->uid));
$from = $resume_user->mail;
$language = user_preferred_language($user);
$contactEmail = node_load($field_contact_email[0][nid]);
$to = "$job_user->mail, $contactEmail";
drupal_mail('job', 'job_apply', $to, $language, $params, $from);
watchdog('job', t("%name applied for job $job_node->nid.",
array('%name' => theme('placeholder', $resume_user->name . " <$from>"))));
}
It seems like it should be a simple thing to do, but I'm struggling!
Cracked it I think :) This sends to both the poster/user's email and one specified in my CCK email field.
function job_send_email($job_nid, $resume_nid) {
global $user;
$params['job_node'] = $job_node = node_load(array('nid' => $job_nid));
$params['job_user'] = $job_user = user_load(array('uid' => $job_node->uid));
$params['resume_node'] = $resume_node = node_load(array('nid' => $resume_nid));
$params['resume_user'] = $resume_user = user_load(array('uid' => $resume_node->uid));
$contactEmail = $job_node->field_contact_email[0]['email'];
$from = $resume_user->mail;
$language = user_preferred_language($user);
$to = "$job_user->mail, $contactEmail";
drupal_mail('job', 'job_apply', $to, $language, $params, $from);
watchdog('job', t("%name applied for job $job_node->nid.",
array('%name' => theme('placeholder', $resume_user->name . " <$from>"))));
}