File Coverage

blib/lib/Mail/MtPolicyd/Plugin/RBL.pm
Criterion Covered Total %
statement 37 39 94.8
branch 10 14 71.4
condition 2 6 33.3
subroutine 7 7 100.0
pod 1 1 100.0
total 57 67 85.0


line stmt bran cond sub pod time code
1             package Mail::MtPolicyd::Plugin::RBL;
2              
3 2     2   1819 use Moose;
  2         3  
  2         11  
4 2     2   8780 use namespace::autoclean;
  2         3  
  2         17  
5              
6             our $VERSION = '2.02'; # VERSION
7             # ABSTRACT: mtpolicyd plugin for checking the client-address against an RBL
8              
9              
10             extends 'Mail::MtPolicyd::Plugin';
11             with 'Mail::MtPolicyd::Plugin::Role::Scoring';
12             with 'Mail::MtPolicyd::Plugin::Role::UserConfig' => {
13             'uc_attributes' => [ 'enabled', 'mode' ],
14             };
15              
16 2     2   225 use Mail::MtPolicyd::Plugin::Result;
  2         3  
  2         35  
17              
18 2     2   380 use Mail::RBL;
  2         82851  
  2         801  
19              
20              
21             has 'domain' => ( is => 'rw', isa => 'Str', required => 1 );
22             has 'enabled' => ( is => 'rw', isa => 'Str', default => 'on' );
23              
24             has 'mode' => ( is => 'rw', isa => 'Str', default => 'reject' );
25              
26             has 'reject_message' => (
27             is => 'ro', isa => 'Str', default => 'delivery from %IP% rejected %INFO%',
28             );
29              
30             has 'score' => ( is => 'rw', isa => 'Maybe[Num]' );
31              
32             has '_rbl' => (
33             is => 'ro', isa => 'Mail::RBL', lazy => 1,
34             default => sub {
35             my $self = shift;
36             Mail::RBL->new($self->domain)
37             },
38             );
39              
40             sub run {
41 5     5 1 443 my ( $self, $r ) = @_;
42 5         172 my $ip = $r->attr('client_address');
43 5         120 my $session = $r->session;
44 5         23 my $mode = $self->get_uc( $session, 'mode' );
45 5         11 my $enabled = $self->get_uc( $session, 'enabled' );
46              
47 5 100       11 if( $enabled eq 'off' ) {
48 1         4 return;
49             }
50            
51             my ( $ip_result, $info ) = $r->do_cached('rbl-'.$self->name.'-result',
52 4     4   108 sub { $self->_rbl->check( $ip ) } );
  4         99  
53              
54 4 100       842382 if( ! defined $ip_result ) {
55 1         39 $self->log($r, 'ip '.$ip.' not on '.$self->domain.' blacklist');
56 1         9 return; # host is not on the list
57             }
58 3 50       141 $self->log($r, 'ip '.$ip.' on '.$self->domain.' blacklist'.( defined $info ? ' ('.$info.')' : '' ) );
59 3 50 33     124 if( defined $self->score && ! $r->is_already_done('rbl-'.$self->name.'-score') ) {
60 3         84 $self->add_score($r, $self->name => $self->score);
61             }
62              
63 3 100       8 if( $mode eq 'reject' ) {
64 2         7 return Mail::MtPolicyd::Plugin::Result->new(
65             action => $self->_get_reject_action($ip, $info),
66             abort => 1,
67             );
68             }
69 1 50       4 if( $mode eq 'accept' ) {
70 0         0 return Mail::MtPolicyd::Plugin::Result->new_dunno;
71             }
72              
73 1         6 return;
74             }
75              
76             sub _get_reject_action {
77 2     2   4 my ( $self, $ip, $info ) = @_;
78 2         58 my $message = $self->reject_message;
79 2         7 $message =~ s/%IP%/$ip/;
80 2 50 33     10 if( defined $info && $info ne '' ) {
81 2         12 $message =~ s/%INFO%/($info)/;
82             } else {
83 0         0 $message =~ s/%INFO%//;
84             }
85 2         82 return('reject '.$message);
86             }
87              
88             __PACKAGE__->meta->make_immutable;
89              
90             1;
91              
92             __END__
93              
94             =pod
95              
96             =encoding UTF-8
97              
98             =head1 NAME
99              
100             Mail::MtPolicyd::Plugin::RBL - mtpolicyd plugin for checking the client-address against an RBL
101              
102             =head1 VERSION
103              
104             version 2.02
105              
106             =head1 DESCRIPTION
107              
108             This plugin queries a DNS black/white list.
109              
110             =head1 PARAMETERS
111              
112             =over
113              
114             =item domain (required)
115              
116             The domain of the blacklist to query.
117              
118             =item (uc_)enabled (default: on)
119              
120             Enable/disable this check.
121              
122             =item (uc_)mode (default: reject)
123              
124             =over
125              
126             =item reject
127              
128             Reject the message. (reject)
129              
130             =item accept
131              
132             Stop processing an accept this message. (dunno)
133              
134             =item passive
135              
136             Only apply the score if one is given.
137              
138             =back
139              
140             =item reject_message (default: delivery from %IP% rejected %INFO%)
141              
142             A pattern for the reject message if mode is set to 'reject'.
143              
144             =item score (default: empty)
145              
146             Apply this score if the check matched.
147              
148             =back
149              
150             =head1 EXAMPLE DNS BLACKLIST
151              
152             <Plugin sorbs.net>
153             module = "RBL"
154             mode = "passive"
155             domain="dnsbl.sorbs.net"
156             score = 5
157             </Plugin>
158              
159             =head1 EXAMPLE DNS WHITELIST
160              
161             <Plugin dnswl.org>
162             module = "RBL"
163             mode = "accept" # will stop here
164             domain="list.dnswl.org"
165             </Plugin>
166              
167             =head1 AUTHOR
168              
169             Markus Benning <ich@markusbenning.de>
170              
171             =head1 COPYRIGHT AND LICENSE
172              
173             This software is Copyright (c) 2014 by Markus Benning <ich@markusbenning.de>.
174              
175             This is free software, licensed under:
176              
177             The GNU General Public License, Version 2, June 1991
178              
179             =cut