Правило срабатывает, если у HTML-части письма нет текстовой альтернативы. Rspamd проверяет это функцией has_only_html_part(): для каждой HTML-части, которая не вложение, ищет соседнюю text/plain в том же multipart/alternative.
Rspamd строже SpamAssassin в одном: важна не только сама текстовая часть, но и где она лежит. Если text/plain и text/html стоят рядом в multipart/mixed, а не внутри multipart/alternative, правило всё равно сработает — для клиента это два разных куска письма, а не две версии одного.
Типичные причины:
Content-Type: text/html;Вес символа в стандартной конфигурации Rspamd — +0.2, группа headers. Администратор сервера может его изменить. Сам по себе он ничего не решает: по умолчанию Rspamd откладывает письмо (greylisting) от 4 баллов, помечает как спам от 6 и отклоняет от 15.
Но Rspamd использует тот же признак и в более тяжёлых правилах. Например, FORGED_OUTLOOK_HTML (+5) срабатывает, когда письмо только в HTML и при этом заявляет, что отправлено из Outlook, — настоящий Outlook всегда добавляет текстовую версию. Если текстовая версия есть, но по смыслу сильно отличается от HTML, сработает R_PARTS_DIFFER.
Отправляйте письмо в формате multipart/alternative: сначала текстовая часть, затем HTML. По RFC 2046 части идут от простой к более богатой, и почтовый клиент показывает последнюю, которую умеет отобразить.
Content-Type: multipart/alternative; boundary="b1"
--b1
Content-Type: text/plain; charset=UTF-8
Здравствуйте, Анна!
Ваш заказ №1234 передан в доставку.
Отследить: https://example.ru/track/1234
--b1
Content-Type: text/html; charset=UTF-8
<html>...свёрстанная версия...</html>
--b1--Если в письме есть вложения или встроенные картинки, multipart/alternative вкладывается внутрь multipart/mixed или multipart/related. Текстовая альтернатива при этом остаётся рядом с HTML.
Python (модуль email):
from email.message import EmailMessage
msg = EmailMessage()
msg["Subject"] = "Ваш заказ передан в доставку"
msg.set_content(text_version) # text/plain
msg.add_alternative(html_version, subtype="html") # text/htmlPHP (PHPMailer):
$mail->isHTML(true);
$mail->Body = $html;
$mail->AltBody = $text; // без AltBody письмо уйдёт только с HTMLЧерез API или конструктор рассылок: заполните поле текстовой версии или включите её автоматическую генерацию из HTML.
Отправьте письмо на адрес из Mail Tester и откройте раздел Rspamd: правило MIME_HTML_ONLY должно пропасть. Структуру письма можно посмотреть и вручную — «Показать оригинал» в Gmail или «Свойства письма» в почтовом клиенте. Ищите multipart/alternative и в нём две части: text/plain и text/html.
То же правило в SpamAssassin: MIME_HTML_ONLY в SpamAssassin. Там же — о расхождении текста и HTML: MPART_ALT_DIFF.
Организует работу поддержки и модерации, помогает клиентам в работе с сервисом.
Руководитель поддержки Mailganer\SaM oTPravil
