File Coverage

blib/lib/Mail/SPF/v2/Record.pm
Criterion Covered Total %
statement 27 49 55.1
branch 0 14 0.0
condition 0 8 0.0
subroutine 9 12 75.0
pod 1 3 33.3
total 37 86 43.0


line stmt bran cond sub pod time code
1             #
2             # Mail::SPF::v2::Record
3             # Sender ID ("spf2.0") record class.
4             #
5             # (C) 2005-2012 Julian Mehnle
6             # 2005 Shevek
7             # $Id: Record.pm 57 2012-01-30 08:15:31Z julian $
8             #
9             ##############################################################################
10              
11             package Mail::SPF::v2::Record;
12              
13             =head1 NAME
14              
15             Mail::SPF::v2::Record - Sender ID ("spf2.0") record class
16              
17             =cut
18              
19 1     1   1122 use warnings;
  1         3  
  1         27  
20 1     1   6 use strict;
  1         3  
  1         32  
21              
22 1     1   5 use base 'Mail::SPF::Record';
  1         2  
  1         76  
23              
24 1     1   5 use constant TRUE => (0 == 0);
  1         3  
  1         60  
25 1     1   6 use constant FALSE => not TRUE;
  1         2  
  1         64  
26              
27 1         53 use constant mech_classes => {
28             all => 'Mail::SPF::Mech::All',
29             ip4 => 'Mail::SPF::Mech::IP4',
30             ip6 => 'Mail::SPF::Mech::IP6',
31             a => 'Mail::SPF::Mech::A',
32             mx => 'Mail::SPF::Mech::MX',
33             ptr => 'Mail::SPF::Mech::PTR',
34             'exists' => 'Mail::SPF::Mech::Exists',
35             include => 'Mail::SPF::Mech::Include'
36 1     1   5 };
  1         2  
37              
38 1         109 use constant mod_classes => {
39             redirect => 'Mail::SPF::Mod::Redirect',
40             'exp' => 'Mail::SPF::Mod::Exp'
41 1     1   5 };
  1         2  
42              
43             eval("require $_")
44             foreach values(%{mech_classes()}), values(%{mod_classes()});
45              
46 1     1   5 use constant valid_scope => qr/^(?: mfrom | pra )$/x;
  1         2  
  1         97  
47 1         557 use constant version_tag_pattern => qr{
48             spf(2\.0)
49             /
50             ( (?: mfrom | pra ) (?: , (?: mfrom | pra ) )* )
51             (?= \x20 | $ )
52 1     1   5 }ix;
  1         2  
53              
54             =head1 SYNOPSIS
55              
56             See L.
57              
58             =head1 DESCRIPTION
59              
60             An object of class B represents a B
61             (C) record.
62              
63             =head2 Constructors
64              
65             The following constructors are provided:
66              
67             =over
68              
69             =item B: returns I
70              
71             Creates a new Sender ID ("spf2.0") record object.
72              
73             %options is a list of key/value pairs representing any of the following
74             options:
75              
76             =over
77              
78             =item B
79              
80             =item B
81              
82             =item B
83              
84             See L.
85              
86             =item B
87              
88             I. See L. The B<'mfrom'> and B<'pra'> scopes
89             are supported. There is no default.
90              
91             =back
92              
93             =cut
94              
95             sub new {
96 0     0 1   my ($self, %options) = @_;
97 0           $self = $self->SUPER::new(%options);
98              
99 0 0         if (not defined($self->{parse_text})) {
100             # No parsing is intended, so scopes should have been specified:
101 0   0       my $scopes = $self->{scopes} || [];
102 0 0         @$scopes > 0
103             or throw Mail::SPF::EInvalidScope('No scopes for spf2.0 record');
104 0           foreach my $scope (@$scopes) {
105 0 0         $scope =~ $self->valid_scope
106             or throw Mail::SPF::EInvalidScope("Invalid scope '$scope' for spf2.0 record");
107             }
108             }
109              
110 0           return $self;
111             }
112              
113             =item B: returns I;
114             throws I, I,
115             I
116              
117             Creates a new Sender ID ("spf2.0") record object by parsing the string and
118             any options given.
119              
120             =back
121              
122             =head2 Class methods
123              
124             The following class methods are provided:
125              
126             =over
127              
128             =item B: returns I
129              
130             Returns a regular expression that matches a version tag of B<'spf2.0/'> plus a
131             comma-separated list of any of the B<'mfrom'> and B<'pra'> scopes. The
132             following are valid version tags:
133              
134             spf2.0/mfrom
135             spf2.0/pra
136             spf2.0/mfrom,pra
137             spf2.0/pra,mfrom
138              
139             =item B
140              
141             =item B
142              
143             See L.
144              
145             =back
146              
147             =head2 Instance methods
148              
149             The following instance methods are provided:
150              
151             =over
152              
153             =cut
154              
155             sub parse_version_tag {
156 0     0 0   my ($self) = @_;
157 0 0         if ($self->{parse_text} =~ s/^${\$self->version_tag_pattern}(?:\x20+|$)//) {
  0            
158 0           my $scopes = $self->{scopes} = [ split(/,/, $2) ];
159 0 0         @$scopes > 0
160             or throw Mail::SPF::EInvalidScope('No scopes for spf2.0 record');
161 0           foreach my $scope (@$scopes) {
162 0 0         $scope =~ $self->valid_scope
163             or throw Mail::SPF::EInvalidScope("Invalid scope '$scope' for spf2.0 record");
164             }
165             }
166             else {
167 0           throw Mail::SPF::EInvalidRecordVersion(
168             "Not a 'spf2.0' record: '" . $self->text . "'");
169             }
170 0           return;
171             }
172              
173             =item B
174              
175             =item B
176              
177             =item B
178              
179             =item B
180              
181             =item B
182              
183             =item B
184              
185             =item B
186              
187             See L.
188              
189             =item B: returns I
190              
191             Returns B<'spf2.0/'> plus a comma-separated list of the scopes of the record.
192             See L for a list of possible return values.
193              
194             =cut
195              
196             sub version_tag {
197 0     0 0   my ($self) = @_;
198 0           return 'spf2.0'
199             if not ref($self) # called as class method
200             or not defined($self->{scopes}) # no scopes parsed
201 0 0 0       or not @{$self->{scopes}}; # no scopes specified in record
      0        
202 0           return 'spf2.0/' . join(',', @{$self->{scopes}});
  0            
203             }
204              
205             =back
206              
207             =head1 SEE ALSO
208              
209             L, L, L, L,
210             L
211              
212             L
213              
214             For availability, support, and license information, see the README file
215             included with Mail::SPF.
216              
217             =head1 AUTHORS
218              
219             Julian Mehnle , Shevek
220              
221             =cut
222              
223             TRUE;