File Coverage

lib/Mail/Toaster/Base.pm
Criterion Covered Total %
statement 104 131 79.3
branch 44 68 64.7
condition 4 8 50.0
subroutine 18 23 78.2
pod 0 19 0.0
total 170 249 68.2


line stmt bran cond sub pod time code
1             package Mail::Toaster::Base;
2 13     13   4939 use strict;
  13         15  
  13         318  
3 13     13   47 use warnings;
  13         19  
  13         436  
4              
5             our $VERSION = '5.50';
6              
7 13     13   46 use Carp;
  13         15  
  13         641  
8 13     13   1182 use Params::Validate ':all';
  13         15126  
  13         17837  
9              
10             our $verbose = our $last_audit = our $last_error = 0; # package variables
11             our (@audit, @errors); # package wide message stacks
12             our ($conf, $log);
13             our ($darwin, $dns, $freebsd, $qmail, $logs, $mysql, $setup, $toaster, $util);
14              
15             our %std_opts = (
16             test_ok => { type => BOOLEAN, optional => 1 },
17             verbose => { type => BOOLEAN, optional => 1, default => $verbose },
18             fatal => { type => BOOLEAN, optional => 1, default => 1 },
19             );
20              
21             sub new {
22 33     33 0 8941 my $class = shift;
23 33         760 my %p = validate( @_, { %std_opts } );
24 33         205 my @caller = caller;
25             # warn sprintf( "Base.pm loaded by %s, %s, %s\n", @caller ) if $caller[0] ne 'main';
26 33         213 return bless {}, $class;
27             }
28              
29             sub darwin {
30 0     0 0 0 my $self = shift;
31 0 0       0 return $darwin if ref $darwin;
32 0         0 require Mail::Toaster::Darwin;
33 0         0 return $darwin = Mail::Toaster::Darwin->new();
34             }
35              
36             sub dns {
37 3     3 0 5 my $self = shift;
38 3 100       15 return $dns if ref $dns;
39 1         552 require Mail::Toaster::DNS;
40 1         9 return $dns = Mail::Toaster::DNS->new();
41             }
42              
43             sub freebsd {
44 0     0 0 0 my $self = shift;
45 0 0       0 return $freebsd if ref $freebsd;
46 0         0 require Mail::Toaster::FreeBSD;
47 0         0 return $freebsd = Mail::Toaster::FreeBSD->new();
48             }
49              
50             sub logs {
51 0     0 0 0 my $self = shift;
52 0 0       0 return $logs if ref $logs;
53 0         0 require Mail::Toaster::Logs;
54 0         0 return $logs = Mail::Toaster::Logs->new();
55             }
56              
57             sub mysql {
58 0     0 0 0 my $self = shift;
59 0 0       0 return $mysql if ref $mysql;
60 0         0 require Mail::Toaster::Mysql;
61 0         0 return $mysql = Mail::Toaster::Mysql->new();
62             }
63              
64             sub qmail {
65 7     7 0 35 my $self = shift;
66 7 100       52 return $qmail if ref $qmail;
67 2         1669 require Mail::Toaster::Qmail;
68 2         26 return $qmail = Mail::Toaster::Qmail->new();
69             }
70              
71             sub setup {
72 3     3 0 4 my $self = shift;
73 3 100       11 return $setup if ref $setup;
74 2         1747 require Mail::Toaster::Setup;
75 2         28 return $setup = Mail::Toaster::Setup->new();
76             }
77              
78             sub toaster {
79 12     12 0 22 my $self = shift;
80 12 100       62 return $toaster if ref $toaster;
81 2         628 require Mail::Toaster;
82 2         17 return $toaster = Mail::Toaster->new();
83             }
84              
85             sub util {
86 40     40 0 3218 my $self = shift;
87 40 100       305 return $util if ref $util;
88 9         6091 require Mail::Toaster::Utility;
89 9         123 return $util = Mail::Toaster::Utility->new();
90             }
91              
92             sub verbose {
93 42 100   42 0 871 return $verbose if 1 == scalar @_;
94 1         5 return $verbose = $std_opts{verbose}{default} = $_[1];
95             };
96              
97             sub conf {
98 214 100   214 0 9313 $conf = $_[1] if $_[1];
99 214 100       908 return $conf if $conf;
100 5         40 $conf = $_[0]->util->parse_config( "toaster-watcher.conf" );
101             };
102              
103             sub audit {
104 368     368 0 1580 my $self = shift;
105 368         422 my $mess = shift;
106              
107 368         5363 my %p = validate( @_, { %std_opts } );
108              
109 368 100       1331 if ($mess) {
110 366         595 push @audit, $mess;
111 366 100 66     1405 print "$mess\n" if $verbose || $p{verbose};
112             }
113              
114 368         979 return \@audit;
115             }
116              
117             sub dump_audit {
118 10     10 0 1482 my $self = shift;
119 10         187 my %p = validate( @_, {
120             quiet => { type => BOOLEAN, optional => 1, default => 0 },
121             %std_opts,
122             }
123             );
124              
125 10 50       56 if ( 0 == scalar @audit ) {
126 0 0       0 print "dump_audit: no audit messages\n" if $p{verbose};
127 0         0 return 1;
128             };
129              
130 10 100       28 if ( $last_audit == scalar @audit ) {
131 1 50       82 print "dump_audit: all messages dumped\n" if $p{verbose};
132 1         6 return 1;
133             };
134              
135 9 100       25 if ( $p{quiet} ) { # hide/mask unreported messages
136 7         16 $last_audit = scalar @audit;
137 7         11 $last_error = scalar @errors;
138 7         25 return 1;
139             };
140              
141 2         267 print "\n\t\t\tAudit History Report \n\n";
142 2         10 for( my $i = $last_audit; $i < scalar @audit; $i++ ) {
143 2         148 print " $audit[$i]\n";
144 2         9 $last_audit++;
145             };
146 2         11 return 1;
147             };
148              
149             sub error {
150 28     28 0 278735 my $self = shift;
151 28 50       101 my $message = shift or carp "why call error w/o message?";
152 28         869 my %p = validate( @_,
153             { location => { type => SCALAR, optional => 1 },
154             frames => { type => SCALAR, optional => 1, default => 0 },
155             %std_opts,
156             },
157             );
158              
159 28 50       175 if ( $message ) {
160             # append message and location to the error stack
161 28         288 my @call = caller $p{frames};
162 28         60 my $location = $p{location};
163 28 50 100     158 if ( ! $location && scalar @call ) {
164 26         95 $location = join( ', ', $call[0], $call[2] );
165             };
166 28         167 push @errors, { errmsg => $message, errloc => $location };
167             }
168             else {
169 0         0 $message = $errors[-1];
170             }
171              
172 28 100       117 $self->dump_audit if $self->verbose;
173 28 100       90 $self->dump_errors if $p{fatal};
174              
175 28 100       402 exit 1 if $p{fatal};
176 25         330 return;
177             }
178              
179             sub dump_errors {
180 6     6 0 21 my $self = shift;
181              
182 6 100       24 if ( $last_error == scalar @errors ) {
183 2 50       14 print "all error messages dumped!\n" if $verbose;
184 2         4 return 1;
185             };
186              
187 4         743 print "\n\t\t\t Error History Report \n\n";
188 4         14 my $i = 0;
189 4         14 foreach ( @errors ) {
190 7         12 $i++;
191 7 100       26 next if $i < $last_error;
192 5         11 my $msg = $_->{errmsg};
193 5 50       30 my $loc = $_->{errloc} ? " at $_->{errloc}" : '';
194 5         279 print $msg;
195 5         30 for (my $j=length($msg); $j < 90-length($loc); $j++) { print '.'; };
  91         1229  
196 5         388 print " $loc\n";
197             };
198 4         133 print "\n";
199 4         20 $last_error = $i;
200 4         12 return 1;
201             };
202              
203             sub get_std_args {
204 191     191 0 234 my $self = shift;
205 191         433 my %p = @_;
206 191         201 my %args;
207 191         344 foreach ( qw/ verbose fatal test_ok / ) {
208 573 100       1028 if ( defined $p{$_} ) {
209 396         429 $args{$_} = $p{$_};
210 396         371 next;
211             };
212 177 50       398 if ( $self->{$_} ) {
213 0         0 $args{$_} = $self->{$_};
214             };
215             };
216 191         680 return %args;
217             };
218              
219 339     339 0 6705 sub get_std_opts { return %std_opts };
220              
221             sub log {
222 0     0 0   my $self = shift;
223 0 0         my $mess = shift or return;
224              
225 0 0         my $logfile = $conf->{'toaster_watcher_log'} or do {
226 0           warn "ERROR: no log file defined!\n";
227 0           return;
228             };
229 0 0 0       return if ( -e $logfile && ! -w $logfile );
230              
231 0           $self->util->logfile_append( $logfile, lines => [$mess], fatal => 0 );
232             };
233              
234             1;