By default, It is defined as
use_article_filter_reject_notice = yes article_filter_reject_notice_recipient = maintainer senderWhen the filter system rejects the request, fml sends back it to both the ML maintainer and the sender.
To change the recipient to the sender (From: address) only, set
article_filter_reject_notice_recipient = sender
To notify the rejection to both ML maintainer and the sender, set
article_filter_reject_notice_recipient = maintainer sender
To disable notification of rejection, set
use_article_filter_reject_notice = no
Case 1: use internal filter.
use_article_spam_filter = yes article_spam_filter_drivers = spamassassin
Case 2: In this case, fml8 use not spamassassin internal filter but use a hook.
$distribute_verify_request_end_hook = q{
my $spamassassin = '/usr/pkg/bin/spamc -c';
use FileHandle;
my $wh = new FileHandle "| $spamassassin";
if (defined $wh) {
$wh->autoflush(1);
my $msg = $curproc->incoming_message();
$msg->print($wh);
$wh->close();
if ($?) {
$curproc->log("spam: (code = $?)");
$curproc->stop_this_process();
}
}
};
$distribute_verify_request_end_hook = q{
my $spamassassin = '/usr/pkg/bin/spamc -c';
use FileHandle;
my $wh = new FileHandle "| $spamassassin";
if (defined $wh) {
$wh->autoflush(1);
my $msg = $curproc->incoming_message();
$msg->print($wh);
$wh->close();
if ($?) {
$curproc->log("spam: (code = $?)");
my $hdr = $curproc->incoming_message_header();
$hdr->add('X-Spam-Status', 'Yes');
}
}
};This is a little tricky but it works well.
fml8 analyzed the incoming message firstly and creates a chain of Mail::Message objects on memory. It is easy for fml8 to analyze the chain to check the message content.
The following examples uses hooks. In all cases, if matched, call stop_this_process() to stop further processing. Pay attension that these examples do not try to return error messsages.
If you need to return error messages, use reply_message(). It is better not to return it since this message must be a virus or a spam.
Here is an example to check attachment keywords e.g. .exe in mesages. Before fml8 2004/12/08 current, it follows:
$distribute_verify_request_start_hook = q{
my $msg = $curproc->incoming_message() || undef;
for (my $m = $msg; $m ; $m = $m->{ next } ) {
my $hs = $m->message_fields() || '';
if ($hs =~ /filename=.*\.(com|vbs|vbe|wsh|wse|js|exe|doc|rtf)/o) {
$curproc->log("attachment \.$1 found");
$curproc->stop_this_process();
}
}
};
After fml8 2004/12/08 current, it follows:
$distribute_verify_request_start_hook = q{
my $msg = $curproc->incoming_message() || undef;
my $list = $msg->message_chain_as_array_ref();
for my $m (@$list) {
my $hs = $m->message_fields() || '';
if ($hs =~ /filename=.*\.(com|vbs|vbe|wsh|wse|js|exe|doc|rtf)/o) {
$curproc->log("[new] attachment \.$1 found");
$curproc->stop_this_process();
}
}
};Another solution is to trap
Content-Disposition: attachment;to detect the existence of attachments. Before fml8 2004/12/08 current, it follows:
$distribute_verify_request_start_hook = q{
my $msg = $curproc->incoming_message() || undef;
for (my $m = $msg; $m ; $m = $m->{ next } ) {
my $hs = $m->message_fields() || '';
if ($hs =~ /Content-Disposition:.*attachment;/o) {
$curproc->log("attachment \.$1 found");
$curproc->stop_this_process();
}
}
};
After fml8 2004/12/08 current, it follows:
$distribute_verify_request_start_hook = q{
my $msg = $curproc->incoming_message() || undef;
my $list = $msg->message_chain_as_array_ref();
for my $m (@$list) {
my $hs = $m->message_fields() || '';
if ($hs =~ /Content-Disposition:.*attachment;/o) {
$curproc->log("[new] attachment \.$1 found");
$curproc->stop_this_process();
}
}
};Copyright (C) 1993-2025 Ken'ichi Fukamachi mail:< fukachan at fml.org >