Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to serve multipart/related content in PHP?

Tags:

php

mime

Say, I have an application/xhtml+xml content and a gif image. How can I serve (not render) these two in a single http get request (using PHP)? It should be a multipart/related content. After reading this RFC, I tried something; but it did not work. (No, I am not trying to send emails with attachment)

Thanks in advance.

EDIT: Finally I succeeded doing that. I think, it will be useful if I write how I did that. I have added this as an answer. Please look below.

like image 659
mshsayem Avatar asked Nov 25 '09 17:11

mshsayem


2 Answers

I'm afraid you can't for the purposes you want.

If you want to do this to serve web pages, as far as I can tell, the browsers won't work with such MIME responses for rendering pages.

If you want an example of how this messages works, send yourself an email with an attachment and on your email client (not an webmail) go to the "View source" option on the email body.

You'll see your message, the attachment and possibly other parts on the same message using the MIME Multipart encoding.

OTOH, if you want it to send email, there are libraries, like PHPMailer, that will do all the encoding for you.
If that's what you want, check this example at their website.

Edit:

You could use PHPMailer to build the message, then you just use the result, instead of actually sending the email.

Try something like this:

** This is untested code, just for a starting point **

<?php
  require_once('../class.phpmailer.php');
  $mail = new PHPMailer(true); // the true param means it will throw exceptions on     errors, which we need to catch

  try {
    $mail->MsgHTML(file_get_contents('contents.html'));
    $mail->AddAttachment('images/phpmailer.gif');      // attachment
    $mail->AddAttachment('images/phpmailer_mini.gif'); // attachment
    $mime_message = $mail->CreateBody();
    echo $mime_message;
  } catch (phpmailerException $e) {
    echo $e->errorMessage(); //Pretty error messages from PHPMailer
  } catch (Exception $e) {
    echo $e->getMessage(); //Boring error messages from anything else!
  }
?>
like image 135
Carlos Lima Avatar answered Oct 26 '22 02:10

Carlos Lima


Here is it [worked for me] (No, I did not used PHPMailer; may be it is useful, but I could not make it working):

// Two contents : application/xhtml+xml and image/gif
// Here we go
<?php
    $boundary = "ghorar#deem";
    $im_len = filesize("path/to/abc.gif")
    header("Content-Type:multipart/related; boundary=\"$boundary\"; type=\"application/xhtml+xml\"");
    $xml_cnt = <<<EOD
<media xmlns="http://www.sth.com/sth.xsd">
    <objectURI>cid:[email protected]</objectURI>
    <size>$im_len</size>
    <type>image/gif</type>
    <name>abcxyz</name>     
    <description>blah blah</description>
</media>
EOD;
    $xml_len = strlen($xml_cnt);        
    $im = imagecreatefromgif("path/to/abc.gif");
    $to_send = "This is a multi-part message example in MIME format

--$boundary
Content-Type: application/xhtml+xml;
Content-ID: <[email protected]>
Content-Length: $xml_len

$xml_cnt
--$boundary
Content-Type: image/gif;
Content-ID: <[email protected]>
Content-Length: $im_Len
Content-Transfer-Encoding: binary

";
    echo $to_send;
    imagegif($im);
    echo "\r\n--$boundary--";
    imagedestroy($im);
?>

You can load the xml from file also. But, note that if your xml refers the image (like I did here) you need to refer that with its Content-ID. Also, note the '<' '>' characters in the Content-ID field of the image (after the boundary) and the 'cid:' notation in the place where it is referred. It worked for me. Thanks to Carlos Lima for spending time for me.

like image 3
mshsayem Avatar answered Oct 26 '22 02:10

mshsayem