Как корректно отправить письмо в php в кодировке UTF-8
Что делать, если стандартная функция php mail() отправляет письма в неверной кодировке.
На самом деле она отправляет что дают и совершенно ничего не проверяет. Что же делать?
Немного теории:
Здесь используется еще и вспомогательная функция mime_header_encode() для преобразования каждого заголовка в MIME-совместимый формат. В PHP предусмотрена аналогичная функция mb_encode_mimeheader(), но она не всегда работает некорректно (возвращает неверный результат) и лучше перестраховаться.
Использование описанной функции достаточно простое. В случае, если кодировка отправки письма отличается от текущей кодировки данных, используется iconv() для преобразования кодировки.
Тело письма может быть текстом в любой кодировке. Немного сложнее дело обстоит с составляющими заголовка письма (Subject, From, To), они по стандарту должны быть в US-ASCII. Использование в заголовках кодированного текста регламентируется стандартом RFC-2047. Стандарт задает две возможные формы кодирования - BASE64 и Quoted-Printable. BASE64 более универсальна и работает в том числе для кодировки UTF-8, поэтому мы будем использовать именно эту форму. MIME-совместимый почтовый клиент обязан уметь читать обе формы.И практика: Ниже приведен пример простой функции, которая отправляет в требуемой кодировке MIME-совместимые письма на русском языке в виде простого текста или в формате HTML
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
<?php function send_mime_mail($name_from, // имя отправителя $email_from, // email отправителя $name_to, // имя получателя $email_to, // email получателя $data_charset, // кодировка переданных данных $send_charset, // кодировка письма $subject, // тема письма $body, // текст письма $html = FALSE // письмо в виде html или обычного текста ) { $to = mime_header_encode($name_to, $data_charset, $send_charset) . ' <' . $email_to . '>'; $subject = mime_header_encode($subject, $data_charset, $send_charset); $from = mime_header_encode($name_from, $data_charset, $send_charset) .' <' . $email_from . '>'; if($data_charset != $send_charset) { $body = iconv($data_charset, $send_charset, $body); } $headers = "From: $from\r\n"; $type = ($html) ? 'html' : 'plain'; $headers .= "Content-type: text/$type; charset=$send_charset\r\n"; $headers .= "Mime-Version: 1.0\r\n"; return mail($to, $subject, $body, $headers); } function mime_header_encode($str, $data_charset, $send_charset) { if($data_charset != $send_charset) { $str = iconv($data_charset, $send_charset, $str); } return '=?' . $send_charset . '?B?' . base64_encode($str) . '?='; } ?> |
1 2 3 4 5 6 7 8 9 10 |
<?php send_mime_mail('Backnet', 'noreply@backnet.ru', 'Получатель письма', 'yourmmail@domain.ru', 'CP1251', // кодировка, в которой находятся передаваемые строки 'KOI8-R', // кодировка, в которой будет отправлено письмо 'Письмо-уведомление', "Здравствуйте, заходите к нам еще!"); ?> |
Кодировку, обозначенную как CP1251 понимают не все клиенты.