2015-07-23 6 views
1


У меня есть проблема с отправкой DKIM подписанного письма с PHPMailer (ст 5.2.9).не может подписать DKIM письма от PHP с PHPMailer

Сервер SMTP, который я использую (realsender.com), должен подписывать каждое электронное письмо, которое я отправляю.
Он работает, когда я отправляю электронное письмо из программы Delphi, но вместо этого он не работает с PHP.

Я проверил как электронную почту, посланную PHPMailer и Delphi с https://www.mail-tester.com

Результаты 10/10 для Delphi и 6,8/10 для PHP.

Это часть файла отправить письмо с PHPMailer:

$mail = new PHPMailer(); 
$mail->CharSet = 'UTF-8'; 
$mail->setLanguage('it'); 
$mail->isSMTP(); 

$mail->Host = SMTP_HOST; 
$mail->SMTPAuth = SMTP_AUTH; 
$mail->Username = SMTP_USERNAME; 
$mail->Password = SMTP_PASSWORD; 
if (defined('SMTP_PORT')) { 
    $mail->Port = SMTP_PORT; 
} 
if (defined('SMTP_SECURE')) { 
    $mail->SMTPSecure = SMTP_SECURE; 
} 
if(defined('DKIM_DOMAIN')){ 
    $mail->DKIM_domain=DKIM_DOMAIN; 
    $mail->DKIM_selector=DKIM_SELECTOR; 
    $mail->DKIM_private=DKIM_PRIVATE; 
} 
[...]//setting from, to, subject and body 
$mail->send(); 

Замечание: при $mail->send(); всегда возвращает истину.

Во-первых, я попытался отправить электронное письмо без установки свойства DKIM_, а затем я попытался отправить с ними.
В обоих случаях результатом является недопустимый знак DKIM и оценка 6.8.

Я попросил поддержку SMTP, если они что-то знают об этом, но они сказали, что это может быть проблема самого PHPMailer.

Что я могу сделать для создания DKIM, который работает?

Заранее спасибо.

UPDATE:
я обнаружил, что проблема заключается в теле письма.
Я также прекратил использовать DKIM_ vars, потому что мой SMTP-сервер автоматически подписывает все электронные письма.
отправка по электронной почте пустой, без тегов или с тегами, но без текста все в порядке (9.9), в противном случае оценка - 6.8.
Также небольшая электронная почта html (со ссылками и divs) в порядке.
Что это может быть?

+0

Вы проверили '' DKIM_ * константы с помощью 'var_dump'? –

+0

Взгляните на [DKIM unit test] (https://github.com/PHPMailer/PHPMailer/blob/master/test/phpmailerTest.php#L1660). Также вы можете получить больше сообщений об ошибках, включив исключения: '$ mail = new PHPMailer (true);'. Последний PHPMailer - 5.2.10, хотя он не имеет изменений, связанных с DKIM. – Synchro

ответ

2

Я понял!
я должен был разделить тело почты на небольшие куски (максимум 990 символов на кусок), причина (объяснение здесь: http://permalink.gmane.org/gmane.mail.postfix.user/223780) является:

Возможной причиной поломки является то, что отправляющее приложение генерирует электронную почту, которая несовместима с RFC 5322 или RFC 5321 в некотором отношении.

линии длиннее, чем 990.

КЛИЕНТ Postfix SMTP хранит длину строки ниже предела протокола SMTP 1000 байт, включая. Поскольку это изменение происходит после подписания, оно, безусловно, нарушит подписи DKIM.

Чтобы избежать проблем с длинной строкой, отправьте почту в кодировке с кавычками или base64 с линиями длиной не более 80 символов.

Это код, который я использовал, чтобы разбить строку:

function create_html_email_from_string($str){ 
    if(!is_string($str)){ 
     return false; 
    } 
    return '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"><html><body>' 
      .html_long_lines_split($str).'</body></html>'; 
} 

/** 
* this function insert line endings (\r\n) after the ending of <br>, <p> and <div> tags because if you only use chunk_split_unicode it can break links and any other tags and css. 
*/ 
function html_long_lines_split($str){ 
    $str = str_ireplace(['<br>','<br/>','<br />'], "<br/>\r\n", $str); 
    $str = str_ireplace('</p>', "</p>\r\n", $str); 
    $str = str_ireplace('</div>', "</div>\r\n", $str); 
    //checks if there are lines longer than 990 bytes 
    $chunks=explode("\r\n", $str); 
    foreach ($chunks as $k=>$c) { 
     if(strlen($chunks[$k])>990){ 
      $chunks[$k]=chunk_split_unicode($chunks[$k], 500); 
     } 
    } 
    return implode("\r\n", $chunks); 
} 

/** 
* @link http://php.net/manual/en/function.chunk-split.php#107711<br> 
*/ 
function chunk_split_unicode($str, $l = 76, $e = "\r\n") { 
    $tmp = array_chunk(
    preg_split("//u", $str, -1, PREG_SPLIT_NO_EMPTY), $l); 
    $str = ""; 
    foreach ($tmp as $t) { 
     $str .= join("", $t) . $e; 
    } 
    return $str; 
} 

//$mail is an instance of PHPMailer 
$mail->msgHTML(create_html_email_from_string($body));