File Coverage

lib/Haineko/SMTPD/Address.pm
Criterion Covered Total %
statement 57 57 100.0
branch 17 20 85.0
condition n/a
subroutine 8 8 100.0
pod 3 3 100.0
total 85 88 96.5


line stmt bran cond sub pod time code
1             package Haineko::SMTPD::Address;
2 4     4   2244 use feature ':5.10';
  4         10  
  4         415  
3 4     4   23 use strict;
  4         8  
  4         117  
4 4     4   20 use warnings;
  4         8  
  4         96  
5 4     4   910 use Class::Accessor::Lite;
  4         1075  
  4         28  
6              
7             my $rwaccessors = [];
8             my $roaccessors = [
9             'address', # (String) Email address
10             'user', # (String) local part of the email address
11             'host', # (String) domain part of the email address
12             ];
13             my $woaccessors = [];
14             Class::Accessor::Lite->mk_accessors( @$roaccessors );
15              
16              
17             sub new {
18 29     29 1 3155 my $class = shift;
19 29         103 my $argvs = { @_ };
20              
21 29 100       98 return undef unless defined $argvs->{'address'};
22              
23 28 100       1980 if( $argvs->{'address'} =~ m{\A(?[^@]+)[@](?[^@]+)\z} ) {
24              
25 27     3   346 $argvs->{'user'} = lc $+{'localpart'};
  3         3626  
  3         1911  
  3         1938  
26 27         174 $argvs->{'host'} = lc $+{'domainpart'};
27              
28 27         104 map { $argvs->{ $_ } =~ y{`'"<>}{}d } keys %$argvs;
  81         181  
29 27         151 $argvs->{'address'} = sprintf( "%s@%s", $argvs->{'user'}, $argvs->{'host'} );
30              
31 27         144 return bless $argvs, __PACKAGE__
32              
33             } else {
34 1         4 return undef;
35             }
36             }
37              
38             sub canonify {
39 26     26 1 167117 my $class = shift;
40 26         141 my $email = shift;
41              
42 26 100       103 return q() unless defined $email;
43 25 100       88 return q() if ref $email;
44              
45             # "=?ISO-2022-JP?B?....?="
46             # no space character between " and < .
47 24         278 $email =~ s/(?.)"
48              
49 24         60 my $canonified = q();
50 24         52 my $addressset = [];
51 24         105 my $emailtoken = [ split ' ', $email ];
52              
53 24         431 for my $e ( @$emailtoken ) {
54             # Convert character entity; "<" -> ">", ">" -> "<".
55 48         91 $e =~ s/</
56 48         65 $e =~ s/>/>/g;
57 48         99 $e =~ s/,\z//g;
58             }
59              
60 24 100       159 if( scalar( @$emailtoken ) == 1 ) {
61             # kijitora@example.jp
62 12         71 push @$addressset, $emailtoken->[0];
63              
64             } else {
65 12         24 foreach my $e ( @$emailtoken ) {
66             # Kijitora cat
67 36         53 chomp $e;
68 36 100       137 next unless $e =~ m{\A[<]?.+[@][-.0-9A-Za-z]+[.][A-Za-z]{2,}[>]?\z};
69 16         74 push @$addressset, $e;
70             }
71             }
72              
73 24 100       61 if( scalar( @$addressset ) > 1 ) {
74             # Get an from string
75 4         11 $canonified = [ grep { $_ =~ m{\A[<].+[>]\z} } @$addressset ]->[0];
  8         32  
76 4 50       14 $canonified = $addressset->[0] unless $canonified;
77              
78             } else {
79             # kijitora@example.jp
80 20         34 $canonified = shift @$addressset;
81             }
82              
83 24 50       68 return q() unless defined $canonified;
84 24 50       54 return q() unless $canonified;
85              
86 24         79 $canonified =~ y{<>[]():;}{}d; # Remove brackets, colons
87 24         36 $canonified =~ y/{}'"`//d; # Remove brackets, quotations
88 24         6770 return $canonified;
89             }
90              
91             sub damn {
92 24     24 1 94 my $self = shift;
93 24         77 my $addr = {
94             'user' => $self->user,
95             'host' => $self->host,
96             'address' => $self->address,
97             };
98 24         1958 return $addr;
99             }
100              
101             1;
102             __END__