Thursday, March 24, 2011

Multipart Email - PHP

Hi,

PHP provides a very simple mechanism for sending emails as compared to other scripting languages. But the problem with emails is, different email client work differently. What I mean to say is, there are many email clients which does not support HTML contents in email. What they do is, they just simply display the HTML tags, instead of parsing them. Now a good solution is to send the emails in plain format. Plain content type is supported by all email clients, irrespective of the fact that whether they support HTML or not.

But the problem with the format of Plain Content type emails, is you cannot create good looking email, with images and hyperlinks, as that will need a HTML content type. So the best solution is to format the email content is such a way that the email clients which support HTML email will show the emails in HTML format and the email client which does not support HTML will show the plain version of the HTML message.

For this you need to use multipart emails. It is very simple. You just need to create two version of the same email. One with the HTML tags and the other without the HTML tags. When you are done doing this, you need to keep few things in mind. Here is an example of multipart email:


<?php
$plain_message_text="This is a plain message:\n\nFor email clients, not supporting HTML\n\nhttp://php-drops.blogspot.com";
$html_message_text="This is a <b>HTML</b> message:<br/><br/>For email clients, supporting <i>HTML</i><br/><br/><a href='http://php-drops.blogspot.com' target='_blank'>PHP Drops</a>";

$notice = "This is a multi-part message in MIME format.";
$boundary = md5(time());


$headers = "From: ".$from_email."\n"
. "MIME-Version: 1.0\n"
 ."Content-Type: multipart/alternative;\n"
 ."     boundary=". chr(34).$boundary. chr(34);
$message = $notice . "\n\n";
$message .= "--" . $boundary."\n";
$message .= "Content-type: text/plain; charset=utf-8\nContent-Transfer-Encoding: 7bit\n\n";
$message .= $plain_message_text. "\n\n";
$message .= "--".$boundary."\n";
$message .= "Content-type: text/html; charset=utf-8\nContent-Transfer-Encoding: 7bit\n\n";
$message .= $html_message_text . "\n\n";
$message .= "--".$boundary."--";
@mail($to, $subject, $message, $headers);
?>

Explanation:

Here I have created two version of the same email. One with HTML, "$html_message_text" and one without HTML tags, "$plain_message_text". You need send both the content in the mail body. But the mail body needs a divider to separate the two formats. For that I have used, $boundary. Now you need to mention $boundary in the email header also as :



$headers = "From: ".$from_email."\n"
. "MIME-Version: 1.0\n"
 ."Content-Type: multipart/alternative;\n"
 ."     boundary=". chr(34).$boundary. chr(34);

chr(34) represents the starting and ending bit for the boundary value. Apart from the divider you need to add the content type definition just before HTML/plain format messages start as:

$message .= "Content-type: text/plain; charset=utf-8\nContent-Transfer-Encoding: 7bit\n\n";
$message .= $plain_message_text. "\n\n";
$message .= "--".$boundary."\n";
$message .= "Content-type: text/html; charset=utf-8\nContent-Transfer-Encoding: 7bit\n\n";
$message .= $html_message_text . "\n\n";
$message .= "--".$boundary."--";

Finally the last thing you need to do is to add a notice, denoting its a multipart email at the beginning of the mail body as:

$message = $notice . "\n\n";  

That's it. Your email will be independent of the email client.

1 comment: