Отправить PHP HTML-почту с вложениями

У меня проблема: до сегодняшнего дня я отправил HTML-письма с PHP, используя заголовок, который содержит

Content-type: text/html; 

Теперь я добавил функциональность для добавления вложений. Для этого мне пришлось изменить эту строку на

 Content-Type: multipart/mixed; 

Теперь, с multipart/mixed , остальная часть почты, поэтому обычный текст отображается так же, как text / plain. Как я могу понять, что вложения работают, а почтовый текст по-прежнему является HTML?

Solutions Collecting From Web of "Отправить PHP HTML-почту с вложениями"

Чтобы отправить электронное письмо с вложением, нам нужно использовать тип MIME с множественным / смешанным, который указывает, что смешанные типы будут включены в электронную почту. Более того, мы хотим использовать многопользовательский / альтернативный тип MIME для отправки как текстовой, так и HTML-версии письма. Посмотрите пример:

 <?php //define the receiver of the email $to = 'youraddress@example.com'; //define the subject of the email $subject = 'Test email with attachment'; //create a boundary string. It must be unique //so we use the MD5 algorithm to generate a random hash $random_hash = md5(date('r', time())); //define the headers we want passed. Note that they are separated with \r\n $headers = "From: webmaster@example.com\r\nReply-To: webmaster@example.com"; //add boundary string and mime type specification $headers .= "\r\nContent-Type: multipart/mixed; boundary=\"PHP-mixed-".$random_hash."\""; //read the atachment file contents into a string, //encode it with MIME base64, //and split it into smaller chunks $attachment = chunk_split(base64_encode(file_get_contents('attachment.zip'))); //define the body of the message. ob_start(); //Turn on output buffering ?> --PHP-mixed-<?php echo $random_hash; ?> Content-Type: multipart/alternative; boundary="PHP-alt-<?php echo $random_hash; ?>" --PHP-alt-<?php echo $random_hash; ?> Content-Type: text/plain; charset="iso-8859-1" Content-Transfer-Encoding: 7bit Hello World!!! This is simple text email message. --PHP-alt-<?php echo $random_hash; ?> Content-Type: text/html; charset="iso-8859-1" Content-Transfer-Encoding: 7bit <h2>Hello World!</h2> <p>This is something with <b>HTML</b> formatting.</p> --PHP-alt-<?php echo $random_hash; ?>-- --PHP-mixed-<?php echo $random_hash; ?> Content-Type: application/zip; name="attachment.zip" Content-Transfer-Encoding: base64 Content-Disposition: attachment <?php echo $attachment; ?> --PHP-mixed-<?php echo $random_hash; ?>-- <?php //copy current buffer contents into $message variable and delete current output buffer $message = ob_get_clean(); //send the email $mail_sent = @mail( $to, $subject, $message, $headers ); //if the message is sent successfully print "Mail sent". Otherwise print "Mail failed" echo $mail_sent ? "Mail sent" : "Mail failed"; ?> 

Как вы можете видеть, отправить электронное письмо с вложением легко. В предыдущем примере у нас есть множественный / смешанный тип MIME, и внутри него мы имеем множественный / альтернативный тип MIME, который указывает две версии электронной почты. Чтобы включить приложение в наше сообщение, мы считываем данные из указанного файла в строку, кодируем его с помощью base64, разбиваем на меньшие куски, чтобы убедиться, что он соответствует спецификациям MIME, а затем включите его в качестве вложения.

Я пробовал ответить 1 на пару часов без везения. Я нашел решение здесь: http://www.finalwebsites.com/forums/topic/php-e-mail-attachment-script

Работает как чары – менее 5 мин! Возможно, вы захотите изменить (например, я), первый тип содержимого из текста / plain в text / html.

Вот моя слегка измененная версия для обработки нескольких вложений:

 function mail_attachment($files, $path, $mailto, $from_mail, $from_name, $replyto, $subject, $message) { $uid = md5(uniqid(time())); $header = "From: ".$from_name." <".$from_mail.">\r\n"; $header .= "Reply-To: ".$replyto."\r\n"; $header .= "MIME-Version: 1.0\r\n"; $header .= "Content-Type: multipart/mixed; boundary=\"".$uid."\"\r\n\r\n"; $header .= "This is a multi-part message in MIME format.\r\n"; $header .= "--".$uid."\r\n"; $header .= "Content-type:text/html; charset=iso-8859-1\r\n"; $header .= "Content-Transfer-Encoding: 7bit\r\n\r\n"; $header .= $message."\r\n\r\n"; foreach ($files as $filename) { $file = $path.$filename; $file_size = filesize($file); $handle = fopen($file, "r"); $content = fread($handle, $file_size); fclose($handle); $content = chunk_split(base64_encode($content)); $header .= "--".$uid."\r\n"; $header .= "Content-Type: application/octet-stream; name=\"".$filename."\"\r\n"; // use different content types here $header .= "Content-Transfer-Encoding: base64\r\n"; $header .= "Content-Disposition: attachment; filename=\"".$filename."\"\r\n\r\n"; $header .= $content."\r\n\r\n"; } $header .= "--".$uid."--"; return mail($mailto, $subject, "", $header); } 

SWIFTMAIL в php работает gr8 для прикрепления с почтой.

Загрузите swiftmailer здесь http://swiftmailer.org/

Посмотрите на простой код ниже

Включить файл

 require_once('path/to/swiftMailer/lib/swift_required.php'); 

СОЗДАТЬ ТРАНСПОРТ

 //FOR SMTP // Create the Transport $transport = Swift_SmtpTransport::newInstance('smtp.googlemail.com', 465, 'ssl') ->setUsername('user@gmail.com') ->setPassword('gmailpassword'); 

ИЛИ

 //FOR NORMAL MAIL $transport = Swift_MailTransport::newInstance(); 

ОБЪЕКТ ОБЪЕКТА

 // Create the Mailer using your created Transport $mailer = Swift_Mailer::newInstance($transport); 

СОЗДАТЬ СООБЩЕНИЕ ОБЪЕКТА

 $message = Swift_Message::newInstance($subject) ->setFrom(array($from => $from)) ->setTo($to) ->setBody($body); $message->attach(Swift_Attachment::fromPath($filepath)); 

ОТПРАВИТЬ СООБЩЕНИЕ

 $result = $mailer->send($message); 

Если вы действительно хотите узнать, как отформатировать интернет-сообщение, тогда вы должны указать свой запрос на комментарии (также известный как RFC). Тот, который определяет «Многоцелевые расширения электронной почты Интернета – формат интернет-сообщений», является RFC2045, выпущенным в ноябре 1996 года.

Формат как-то очень строгий и должен соблюдаться как есть.

В основном сообщение содержит заголовок и тело. Заголовок определяет тип сообщения, способ его формирования, некоторые другие поля, которые отличаются от одного типа к другому.

Тело образовано разными сущностями. Сущность может быть, например, просто текстовым, например «Hello there!» но также может быть образ, привязанность, что угодно.

ПРИМЕЧАНИЕ. В следующих примерах все заключенные в скобки (например, {hello}) должны быть заменены на ваше реальное значение. Любая новая строка на самом деле является CRLF (т.е. ASCII 13 + ASCII 10). Где вы видите два CRLF. Было бы худшим моментом, чтобы показать, насколько вы творческий.

В основном для сообщения электронной почты, имеющего вложения, заголовок должен выглядеть следующим образом:

 MIME-Version: 1.0 To: {email@domain} Subject: {email-subject} X-Priority: {2 (High)} Content-Type: multipart/mixed; boundary="{mixed-boudary}" 

В приведенном выше примере {mixed-boudary} может быть любым уникальным значением хэша, например 000008050800060107020705. Остальные не требуют пояснений.

Теперь, в любое время, когда мы хотим добавить новый объект в сообщение (например, тело сообщения, изображение, вложение), мы должны сообщить агенту электронной почты о появлении нового раздела , т.е. для префикса этого объекта значением {mixed-border}. Мы называем это «открываем границу». Обратите внимание, что, открыв границу, мы не вставляем эту границу, как было определено первоначально, мы используем еще два минусовых знака спереди, например – {mixed-boudary}. Когда мы закрываем границу, мы идем аналогично, за исключением того, что в конце мы должны использовать другие 2 минус-знака, например – {mixed-boudary} –

 --{mixed-boudary} the entity content --{mixed-boudary}-- 

Поскольку агент электронной почты должен понимать, какой тип имеет содержание нашего нового вставленного объекта, мы должны объявить это сразу после открытия границы. Объявление – это просто заголовок, который содержит только те параметры / значения, которые совместимы с объектом.

Для содержимого тела HTML заголовок моего объекта будет выглядеть так:

 Content-Type: text/html; charset=utf-8 Content-Transfer-Encoding: 7bit 

так что все тело (заключенное в границы), наконец, будет выглядеть так:

 --{mixed-boudary} Content-Type: text/html; charset=utf-8 Content-Transfer-Encoding: 7bit <html> <head><meta http-equiv="content-type" content="text/html; charset=utf-8"></head> <body bgcolor="#FFFFFF" text="#000000"> Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque vel dapibus arcu. Duis quam dui, ornare non mi nec, luctus faucibus massa. Vivamus quis purus in erat euismod ullamcorper vitae eget dolor. Aliquam tempor erat accumsan, consectetur ex et, rhoncus risus. </body> </html> 

Если нужно добавить другой объект, мы будем действовать точно так же, как указано выше. Когда больше нет данных для добавления в сообщение, мы закрываем смешанную границу, т. Е. CRLF + – {mixed-boudary} -.

Если по какой-либо причине объект должен быть вставлен с альтернативным представлением (например, сообщение тела вставляется как в виде текстового формата, так и в формате HTML), тогда контент объекта должен быть объявлен с использованием многотипного / альтернативного типа контента (хотя глобальный многочастный / смешанный заголовок все еще остается!). Каждое альтернативное представление будет заключено в эту новую границу.

Полный пример ниже:

 MIME-Version: 1.0 To: {email@domain} Subject: {email-subject} X-Priority: {2 (High)} Content-Type: multipart/mixed; boundary="{mixed-boudary}" --{mixed-boudary} Content-Type: multipart/alternative; boundary="{alternative-boudary}" --{alternative-boudary} Content-Type: text/plain; charset=utf-8; Content-Transfer-Encoding: 7bit Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque vel dapibus arcu. Duis quam dui, ornare non mi nec, luctus faucibus massa. Vivamus quis purus in erat euismod ullamcorper vitae eget dolor. Aliquam tempor erat accumsan, consectetur ex et, rhoncus risus. --{alternative-boudary} Content-Type: text/html; charset=utf-8; Content-Transfer-Encoding: 7bit <html> <head><meta http-equiv="content-type" content="text/html; charset=utf-8"></head> <body bgcolor="#FFFFFF" text="#000000"> Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque vel dapibus arcu. Duis quam dui, ornare non mi nec, luctus faucibus massa. Vivamus quis purus in erat euismod ullamcorper vitae eget dolor. Aliquam tempor erat accumsan, consectetur ex et, rhoncus risus. </body> </html> --{alternative-boudary}-- --{mixed-boudary} Content-Type: application/pdf; name="myfile.pdf" Content-Transfer-Encoding: base64 Content-Disposition: attachment; filename="myfile.pdf" JVBERi0xLjINOCAwIG9iag08PCAvTGVuZ3RoIDkgMCBSIC9GaWx0ZXIgL0ZsYXRlRGVjb2Rl ID4+DXN0cmVhbQ1oQ51bbY/cNg7+BfsfhAUO11w3riW/B7gPaZEAAdpcm06RL8EBzoyn68uM vZ3xZLv//khKsuUxNaMNiiabpUg+pKiHsmxJEcN/UsgiilP4ab2/+XF1I81vszSqclHIOEpj sdrf/PC2EFVUpmK1vXkZxVKs1uJlJJVYPYrvPra7XVvvxYdIrE7rL83hhVj97+bNyjUoFam7 FnOB+tubGI3FZEkwmhpKXpVRnqJi0PCyjBJ1DjyOYqWBxxXp/1h3X+ov9abZt434pV0feoG/ ars/xU/9/qEZmm7diJ+abmgOr0TGeFNFEuXx5M4B95Idns/QAaJMI1IpKeXi9+ZhaPafm4NQ cRwzNpK0iirlRvisRBZpVJa+PP51091kkjBWBXrJxUuZRjIXh0Z8FN3MnB5X5st5Kay9355n --{mixed-boudary}-- 

ЧАЕВЫЕ

Используйте свой предпочтительный почтовый клиент (мой Thunderbird) и отправляйте себе одно сообщение только с открытым текстом, только один HTML, один смешанный, а затем каждый из ранних, но с одним прикрепленным файлом. Когда вы получаете сообщение, просто изучите его источник (View -> Message source).

@Edit: очень хорошо документированное тематическое исследование + пример PHP можно найти здесь