File Coverage

blib/lib/Mail/TLSRPT/Report.pm
Criterion Covered Total %
statement 94 98 95.9
branch 5 8 62.5
condition n/a
subroutine 20 20 100.0
pod 0 7 0.0
total 119 133 89.4


line stmt bran cond sub pod time code
1             package Mail::TLSRPT::Report;
2             # ABSTRACT: TLSRPT report object
3             our $VERSION = '1.20200306.1'; # VERSION
4 6     6   4260 use 5.20.0;
  6         24  
5 6     6   31 use Moo;
  6         14  
  6         89  
6 6     6   1901 use Carp;
  6         65  
  6         366  
7 6     6   38 use Mail::TLSRPT::Pragmas;
  6         12  
  6         36  
8 6     6   3757 use Mail::TLSRPT::Policy;
  6         19  
  6         198  
9 6     6   48 use Mail::TLSRPT::Failure;
  6         12  
  6         119  
10 6     6   5581 use DateTime;
  6         2968633  
  6         341  
11 6     6   3654 use Date::Parse qw{ str2time };
  6         43567  
  6         544  
12 6     6   3819 use IO::Uncompress::Gunzip;
  6         277756  
  6         351  
13 6     6   4709 use Text::CSV;
  6         84784  
  6         7045  
14             has organization_name => (is => 'rw', isa => Str, required => 1);
15             has start_datetime => (is => 'rw', isa => class_type('DateTime'), required => 1);
16             has end_datetime => (is => 'rw', isa => class_type('DateTime'), required => 1);
17             has contact_info => (is => 'rw', isa => Str, required => 1);
18             has report_id => (is => 'rw', isa => Str, required => 1);
19 1     1   11834 has policies => (is => 'rw', isa => ArrayRef, required => 0, lazy => 1, builder => sub{return []} );
20              
21 6     6 0 10594 sub new_from_json($class,$json) {
  6         15  
  6         13  
  6         12  
22 6         73 my $j = JSON->new;
23 6         154 my $data = $j->decode($json);
24 6         27 return $class->new_from_data($data);
25             }
26              
27 1     1 0 4563 sub new_from_json_gz($class,$compressed_json) {
  1         3  
  1         2  
  1         2  
28 1         2 my $json;
29 1         9 IO::Uncompress::Gunzip::gunzip(\$compressed_json,\$json);
30 1         2596 return $class->new_from_json($json);
31             }
32              
33 7     7 0 4883 sub new_from_data($class,$data) {
  7         14  
  7         16  
  7         125  
34 7         54 my @policies;
35 7         32 foreach my $policy ( $data->{policies}->@* ) {
36 5         37 push @policies, Mail::TLSRPT::Policy->new_from_data($policy);
37             }
38             my $self = $class->new(
39             organization_name => $data->{'organization-name'},
40             start_datetime => DateTime->from_epoch(epoch => str2time($data->{'date-range'}->{'start-datetime'})),
41             end_datetime => DateTime->from_epoch(epoch => str2time($data->{'date-range'}->{'end-datetime'})),
42             contact_info => $data->{'contact-info'},
43 7         56 report_id => $data->{'report-id'},
44             policies => \@policies,
45             );
46 7         25097 return $self;
47             }
48              
49 3     3 0 2750 sub as_json($self) {
  3         7  
  3         5  
50 3         14 my $j = JSON->new;
51 3         21 $j->canonical;
52 3         10 return $j->encode( $self->as_struct );
53             }
54              
55 5     5 0 1454 sub as_struct($self) {
  5         12  
  5         8  
56 5         128 my @policies = map {$_->as_struct} $self->policies->@*;
  3         37  
57             return {
58 5 100       494 'organization-name' => $self->organization_name,
59             'date-range' => {
60             'start-datetime' => $self->start_datetime->datetime.'Z',
61             'end-datetime' => $self->end_datetime->datetime.'Z',
62             },
63             'contact-info' => $self->contact_info,
64             'report-id' => $self->report_id,
65             scalar $self->policies->@* ? ( policies => \@policies ) : (),
66             };
67             }
68              
69 4     4 0 10824 sub as_string($self) {
  4         10  
  4         8  
70             return join( "\n",
71             'Report-ID: <'.$self->report_id.'>',
72             'From: "'.$self->organization_name.'" <'.$self->contact_info.'>',
73             'Dates: '.$self->start_datetime->datetime.'Z to '.$self->end_datetime->datetime.'Z',
74 4         101 map { $_->as_string } $self->policies->@*,
  1         187  
75             );
76             }
77              
78 1     1   3 sub _csv_headers($self) {
  1         1  
  1         2  
79             return (
80 1         6 'report id',
81             'organization name',
82             'start date time',
83             'end date time',
84             'contact info',
85             );
86             }
87              
88 3     3   6 sub _csv_fragment($self) {
  3         4  
  3         6  
89             return (
90 3         57 $self->report_id,
91             $self->organization_name,
92             $self->start_datetime->datetime.'Z',
93             $self->end_datetime->datetime.'Z',
94             $self->contact_info,
95             );
96             }
97              
98 1     1 0 746 sub as_csv($self,$args) {
  1         2  
  1         2  
  1         2  
99 1         2 my @output;
100 1         7 my $csv = Text::CSV->new;
101 1 50       160 if ( $args->{add_header} ) {
102 1         4 $csv->combine($self->_csv_headers,Mail::TLSRPT::Policy->_csv_headers,Mail::TLSRPT::Failure->_csv_headers);
103 1         44 push @output, $csv->string;
104             }
105 1 50       35 if ( scalar $self->policies->@* ) {
106 1         26 foreach my $policy ( $self->policies->@* ) {
107 1 50       23 if ( scalar $policy->failures->@* ) {
108 1         23 foreach my $failure ( $policy->failures->@* ) {
109 3         26 $csv->combine($self->_csv_fragment,$policy->_csv_fragment,$failure->_csv_fragment);
110 3         600 push @output, $csv->string;
111             }
112             }
113             else {
114 0         0 $csv->combine($self->_csv_fragment,$policy->_csv_fragment);
115 0         0 push @output, $csv->string;
116             }
117             }
118             }
119             else {
120 0         0 $csv->combine($self->_csv_fragment);
121 0         0 push @output, $csv->string;
122             }
123 1         28 return join( "\n", @output );
124             }
125              
126             1;
127              
128             __END__
129              
130             =pod
131              
132             =encoding UTF-8
133              
134             =head1 NAME
135              
136             Mail::TLSRPT::Report - TLSRPT report object
137              
138             =head1 VERSION
139              
140             version 1.20200306.1
141              
142             =head1 AUTHOR
143              
144             Marc Bradshaw <marc@marcbradshaw.net>
145              
146             =head1 COPYRIGHT AND LICENSE
147              
148             This software is copyright (c) 2020 by Marc Bradshaw.
149              
150             This is free software; you can redistribute it and/or modify it under
151             the same terms as the Perl 5 programming language system itself.
152              
153             =cut