地方バス会社のお知らせメールがスパム判定されてしまいました。
SpamAssassinの誤判定を解消する方法を考えてみます。
うちでは5.0以上でスパムなので、スパム扱いで、件名に ***** SPAM ***** がついてしまいます。
SpamAssassinがつけたスコアは5.6でした。
メールヘッダにX-Spam-Status: Yesがあれば自動的にゴミ箱行きフィルタを設定している人は、このメールを見ることができなかったでしょう。
ヘッダにあるレポートは以下のとおりでした。
Content analysis details: (5.6 points, 5.0 required) pts rule name description ---- ---------------------- -------------------------------------------------- -0.0 SPF_PASS SPF: sender matches SPF record -0.0 RCVD_IN_DNSWL_NONE RBL: Sender listed at https://www.dnswl.org/, no trust [nnn.nnn.nnn.nnn listed in list.dnswl.org] 2.0 PYZOR_CHECK Listed in Pyzor (https://pyzor.readthedocs.io/en/latest/) 1.4 KHOP_DYNAMIC Relay looks like a dynamic address 2.3 BODY_SINGLE_WORD Message body is only one word (no spaces)
大手キャリアを使ったメールではないので、若干スコアが上がるのは仕方がないでしょう。
しかし、BODY_SINGLE_WORDでスコア2.3が加算されています。
descriptionにあるとおり、本文が「1語」しか無いのが理由なようです。
本文は以下のとおりでした。
〇〇交通ニュース第123号を配信します。
どこが「1語」?
英語の場合は単語を空白で繋いで文章にします。
スペースを含まない日本語の1文は、長くても「1語」に判定されてしまうんですね。
これはいけません。
BODY_SINGLE_WORDに対するスコア設定はどこにあるんだ?
設定ディレクトリ/etc/spamassassin/を探したのですが、見つかりませんでした。
ビルトインルールなので、設定の中にはないんですね。
SpamAssassinのプログラムの中にありました。
# grep BODY_SINGLE_WORD -rl /usr/share/spamassassin/
で以下の2行が出てきました。
/usr/share/spamassassin/72_active.cf /usr/share/spamassassin/72_scores.cf
72_scores.cfのなかに
score BODY_SINGLE_WORD 2.500 0.689 2.500 0.689
とありました。
スペースで区切られたスコアが4個もありますが、どういうことでしょうか。
72_active.cfに
#score BODY_SINGLE_WORD 2.500 # limit
とあるのは、最大2.5で、なんにかの要因で加減されるということなのでしょうか。
72_scores.cfを編集してもっと低いスコアに変えましょう。
ところが、
72_active.cfファイルの最初にこうあります。
# Please don't modify this file as your changes will be overwritten with # the next update. Use @@LOCAL_RULES_DIR@@/local.cf instead. # See 'perldoc Mail::SpamAssassin::Conf' for details.
このファイルを変更しないでください。変更してもSpamAssassinのアップデートのときに上書きされます。 local.cfを使ってください。 詳しいことは'perldoc Mail::SpamAssassin::Conf'をみてください。
なるほど、マニュアルを確認するのは基本ですね。
それでは、さっそく…
$ perldoc Mail::SpamAssassin::Conf You need to install the perl-doc package to use this program.
perl-docがないと怒られました。
インストールします。
$ sudo apt install perl-doc
再度挑戦。
$ perldoc Mail::SpamAssassin::Conf
NAME Mail::SpamAssassin::Conf - SpamAssassin configuration file SYNOPSIS # a comment rewrite_header Subject *****SPAM***** full PARA_A_2_C_OF_1618 /Paragraph .a.{0,10}2.{0,10}C. of S. 1618/i describe PARA_A_2_C_OF_1618 Claims compliance with senate bill 1618 header FROM_HAS_MIXED_NUMS From =~ /\d+[a-z]+\d+\S*@/i describe FROM_HAS_MIXED_NUMS From: contains numbers mixed in with letters ....
2000行以上のマニュアルが表示されました。
とても全部読めないので、このマニュアルの先頭部分を読んでみました。
そこからわかったことは、
- 72_scores.cfにあるような4個のスコアは、Baysやネットワークテストの設定によってどのスコアを使うかが変わる。
- スコアをひとつだけ設定すれば、それが全状況で使われる。
- スコアを0にすると、そのテストは無効になる。
- スコア値を括弧()で囲むと、相対値として既存のスコアを加減する。
- スコアを設定していない場合は1.0を設定したことになる。
SpamAssassin設定ファイルはデフォルトで/usr/share/spamassassinと/etc/mail/spamassassinにあります。
Debianなどのディストリビューションでは、/etc/mail/spamassassinが/etc/spamassassinにリンクされています。
- 拡張子が.cfのファイルはすべてSpamAssassinの起動時にアルファベット順に読み込まれます。
- あとから読み込むもので、設定値が上書きされます。
今回のBODY_SINGLE_WORDもあとから読み込まれるファイルに改めて定義してやればいいんですね。
今回は無効にしてしまいます。
日本語メールを中心に扱う場合は、BODY_SINGLE_WORDは必要ないと思います。
海外からのスパムで本文が1単語だけというのは見たことがありません。
メールをチャット代わりに使う職場などの場合は、なおさら設定しないほうが無難です。
score BODY_SINGLE_WORD 0
SpamAssassinに限ったことでな無いのですが、マニュアルを読むのが一番の早道ですね。
ただ、それが英語で、日々アップデートされるソフトウエアに追いついていなかったりするのが憂鬱ですが。