Projekt

Allgemein

Profil

« Zurück | Weiter » 

Revision 958c1727

Von Bernd Bleßmann vor mehr als 3 Jahren hinzugefügt

  • ID 958c1727a1453b28feaf8c4bfa40ef25f8bcc3ea
  • Vorgänger 20615592
  • Nachfolger f9c38bb5

S:C:H:ReportGenerator: Interface und Impmentierung von Kontroll-Zeilen

Es wurde eine Schnittstelle geschaffen, um Kontroll-Zeilen an den
ReportGenerator-Helfer zu übergeben.
Umgesetzt sind Kontroll-Zeilen für einen Separator und für eigene Daten.

Unterschiede anzeigen:

SL/Controller/Helper/ReportGenerator.pm
4 4

  
5 5
use Carp;
6 6
use List::Util qw(max);
7
use Scalar::Util qw(blessed);
7 8

  
8 9
use SL::Common;
9 10
use SL::MoreCommon;
......
126 127
  my @columns     = $params{report}->get_visible_columns('HTML');
127 128

  
128 129
  for my $obj (@{ $params{objects} || [] }) {
129
    my %data = map {
130
      my $def = $column_defs->{$_};
131
      my $tmp;
132
      $tmp->{raw_data} = $def->{raw_data} ? $def->{raw_data}->($obj) : '';
133
      $tmp->{data}     = $def->{sub}      ? $def->{sub}->($obj)
134
                       : $obj->can($_)    ? $obj->$_
135
                       :                    $obj->{$_};
136
      $tmp->{link}     = $def->{obj_link} ? $def->{obj_link}->($obj) : '';
137
      $_ => $tmp;
138
    } @columns;
130
    my %data;
131

  
132
    if (blessed($obj) && $obj->isa('SL::Controller::Helper::ReportGenerator::ControlRow::Base')) {
133
      $obj->set_data($params{report});
134
      next;
135

  
136
    } else {
137
      %data = map {
138
        my $def = $column_defs->{$_};
139
        my $tmp;
140
        $tmp->{raw_data} = $def->{raw_data} ? $def->{raw_data}->($obj) : '';
141
        $tmp->{data}     = $def->{sub}      ? $def->{sub}->($obj)
142
                         : $obj->can($_)    ? $obj->$_
143
                         :                    $obj->{$_};
144
        $tmp->{link}     = $def->{obj_link} ? $def->{obj_link}->($obj) : '';
145
        $_ => $tmp;
146
      } @columns;
147
    }
139 148

  
140 149
    $params{data_callback}->(\%data) if $params{data_callback};
141 150

  
......
251 260

  
252 261
Mandatory. An array reference of RDBO models to output.
253 262

  
263
An element of the array can also be an instance of a control row, i.e.
264
an instance of a class derived from
265
C<SL::Controller::Helper::ReportGenerator::ControlRow::Base>.
266
See also:
267

  
268
L<SL::Controller::Helper::ReportGenerator::ControlRow>
269
L<SL::Controller::Helper::ReportGenerator::ControlRow::*>
270

  
254 271
=item C<data_callback>
255 272

  
256 273
Optional. A callback handler (code reference) that gets called for
SL/Controller/Helper/ReportGenerator/ControlRow.pm
1
package SL::Controller::Helper::ReportGenerator::ControlRow;
2

  
3
use strict;
4
use Carp;
5

  
6
use SL::Controller::Helper::ReportGenerator::ControlRow::ALL;
7

  
8
use Exporter 'import';
9
our @EXPORT = qw(
10
  make_control_row
11
);
12

  
13

  
14
sub make_control_row {
15
  my ($type, %args) = @_;
16

  
17
  my $class  = $SL::Controller::Helper::ReportGenerator::ControlRow::ALL::type_to_class{$type} // croak "unknown type $type";
18
  my $obj    = $class->new(params => \%args);
19
  my @errors = $obj->validate_params;
20
  croak join("\n", @errors) if @errors;
21

  
22
  return $obj;
23
}
24

  
25

  
26
1;
27

  
28
__END__
29

  
30
=encoding utf-8
31

  
32
=head1 NAME
33

  
34
SL::Controller::Helper::ReportGenerator::ControlRow - an interface for
35
report generator control rows
36

  
37
=head1 DESCRIPTION
38

  
39
ControlRow is an interface that allows generic control rows to be added
40
to objects for the C<SL::Controller::Helper::ReportGenerator>.
41

  
42
Each control row implementation can access the report and add data for a row.
43

  
44
=head1 SYNOPSIS
45

  
46
  package SL::Controller::TimeRecording;
47

  
48
  use SL::Controller::Helper::ReportGenerator;
49
  use SL::Controller::Helper::ReportGenerator::ControlRow qw(make_control_row);
50

  
51
  sub action_list {
52
    my ($self) = @_;
53

  
54
    # Set up the report generator instance. In this example this is
55
    # hidden in "prepare_report".
56
    my $report = $self->prepare_report;
57

  
58
    # Get objects from database.
59
    my $objects = SL::DB::Manager::TimeRecording->get_all(...);
60

  
61
    # Add a separator
62
    push @$objects, make_control_row("separator");
63

  
64
    # And a simple total
65
    my $total = sum0 map { _round_total($_->duration_in_hours) } @$objects;
66
    push @$objects, make_control_row("simple_data", data => {duration => $total});
67

  
68
    # Let report generator create the output.
69
    $self->report_generator_list_objects(
70
      report  => $report,
71
      objects => $objects,
72
    );
73
  }
74

  
75

  
76
=head1 WRITING OWN CONTROL ROW CLASSES
77

  
78
See C<SL::Controller::Helper::ReportGenerator::ControlRow::Base>.
79

  
80
=head1 FUNCTIONS
81

  
82
=over 4
83

  
84
=item C<make_control_row TYPE %PARAMS>
85

  
86
Returns an instance of the control row class for the given type. This
87
object can be used as an element of objects to the report generator helper
88
(see C<SL::Controller::Helper::ReportGenerator>).
89

  
90
Available types are 'separator', 'data, 'simple_data' for now.
91

  
92
C<%PARAMS> depends on the type. See also:
93

  
94
L<SL::Controller::Helper::ReportGenerator::ControlRow::ALL>
95
L<SL::Controller::Helper::ReportGenerator::ControlRow::*>
96

  
97
=back
98

  
99
=head1 AUTHOR
100

  
101
Bernd Bleßmann E<lt>bernd@kivitendo-premium.deE<gt>
102

  
103
=cut
SL/Controller/Helper/ReportGenerator/ControlRow/ALL.pm
1
package SL::Controller::Helper::ReportGenerator::ControlRow::ALL;
2

  
3
use strict;
4

  
5
use SL::Controller::Helper::ReportGenerator::ControlRow::Data;
6
use SL::Controller::Helper::ReportGenerator::ControlRow::Separator;
7
use SL::Controller::Helper::ReportGenerator::ControlRow::SimpleData;
8

  
9
our %type_to_class = (
10
  data        => 'SL::Controller::Helper::ReportGenerator::ControlRow::Data',
11
  separator   => 'SL::Controller::Helper::ReportGenerator::ControlRow::Separator',
12
  simple_data => 'SL::Controller::Helper::ReportGenerator::ControlRow::SimpleData',
13
);
14

  
15
1;
SL/Controller/Helper/ReportGenerator/ControlRow/Base.pm
1
package SL::Controller::Helper::ReportGenerator::ControlRow::Base;
2

  
3
use strict;
4

  
5
use parent qw(SL::DB::Object);
6

  
7
use Rose::Object::MakeMethods::Generic (
8
  scalar => [ qw(params) ],
9
);
10

  
11

  
12
sub validate_params { die 'name needs to be implemented' }
13
sub set_data        { die 'name needs to be implemented' }
14

  
15

  
16
1;
17

  
18

  
19
__END__
20

  
21
=encoding utf-8
22

  
23
=head1 NAME
24

  
25
SL::Controller::Helper::ReportGenerator::ControlRow::Base - a base class
26
for report generator control row classes
27

  
28
=head1 DESCRIPTION
29

  
30
ControlRow is an interface that allows generic control rows to be added
31
to objects for the C<SL::Controller::Helper::ReportGenerator>. This is a
32
base class from which all control row classes are derived.
33

  
34
=head1 SYNOPSIS
35

  
36
Adding your own new control row of the type "only_dashes":
37

  
38
  package SL::Controller::Helper::ReportGenerator::ControlRow::OnlyDashes;
39

  
40
  use parent qw(SL::Controller::Helper::ReportGenerator::ControlRow::Base);
41

  
42
  sub validate_params { return; } # no params
43

  
44
  sub set_data {
45
    my ($self, $report) = @_;
46

  
47
    my %data = map { $_ => {data => '---'} } keys %{ $report->{columns} };
48

  
49
    $report->add_data(\%data);
50
  }
51

  
52
After that, you have to register your new class in
53
C<SL::Controller::Helper::ReportGenerator::ControlRow::ALL>:
54

  
55
  use SL::Controller::Helper::ReportGenerator::ControlRow::OnlyDashes;
56

  
57
  our %type_to_class = (
58
    ...,
59
    only_dashes => 'SL::Controller::Helper::ReportGenerator::ControlRow::OnlyDashes',
60
  );
61

  
62

  
63
=head1 WRITING OWN CONTROL ROW CLASSES
64

  
65
You can use C<SL::Controller::Helper::ReportGenerator::ControlRow::Base>
66
as parent of your module. You have to provide two methods:
67

  
68
=over 4
69

  
70
=item C<validate_params>
71

  
72
This method is used to validate any params used for your module.
73
You can access the params through the method C<params> which contains all
74
remaining params after the type of the call to make_control_row (see
75
C<SL::Controller::Helper::ReportGenerator::ControlRow>).
76

  
77
The method should return an array of error messages if there are any
78
errors. Otherwise it should return C<undef>.
79

  
80
=item C<set_data REPORT>
81

  
82
This method sould set the data for the report generator, which is handeled
83
over as argument.
84

  
85
=back
86

  
87
=head1 REGISTERING OWN CONTROL ROW CLASSES
88

  
89
See C<SL::Controller::Helper::ReportGenerator::ControlRow::ALL>. Here your
90
class should be included with C<use> and entered in the map C<%type_to_class>
91
with an appropiate name for it's type.
92

  
93

  
94
=head1 AUTHOR
95

  
96
Bernd Bleßmann E<lt>bernd@kivitendo-premium.deE<gt>
97

  
98
=cut
SL/Controller/Helper/ReportGenerator/ControlRow/Data.pm
1
package SL::Controller::Helper::ReportGenerator::ControlRow::Data;
2

  
3
use strict;
4

  
5
use parent qw(SL::Controller::Helper::ReportGenerator::ControlRow::Base);
6

  
7

  
8
sub validate_params {
9
  my ($self) = @_;
10

  
11
  my @errors;
12
  push @errors, 'type "data" needs a parameter "row" as hash ref' if !$self->params->{row} || ('HASH' ne ref $self->params->{row});
13

  
14
  return @errors;;
15
}
16

  
17
sub set_data {
18
  my ($self, $report) = @_;
19

  
20
  my %data;
21
  %data = map {
22
    my $def = $self->params->{row}->{$_};
23
    my $tmp;
24

  
25
    foreach my $attr (qw(raw_data data link class align)) {
26
      $tmp->{$attr} = $def->{$attr} if defined $def->{$attr};
27
    }
28
    $_ => $tmp;
29
  } keys %{ $self->params->{row} };
30

  
31
  $report->add_data(\%data);
32
}
33

  
34

  
35
1;
36

  
37
__END__
38

  
39
=encoding utf-8
40

  
41
=head1 NAME
42

  
43
SL::Controller::Helper::ReportGenerator::ControlRow::Data - an
44
implementaion of a control row class to display data
45

  
46
=head1 DESCRIPTION
47

  
48
This class implements a control row for the report generator helper to display
49
data. You can configure the way the data is displayed.
50

  
51
=head1 SYNOPSIS
52

  
53
  use SL::Controller::Helper::ReportGenerator;
54
  use SL::Controller::Helper::ReportGenerator::ControlRow qw(make_control_row);
55

  
56
  sub action_list {
57
    my ($self) = @_;
58

  
59
    # Set up the report generator instance. In this example this is
60
    # hidden in "prepare_report".
61
    my $report = $self->prepare_report;
62

  
63
    # Get objects from database.
64
    my $objects = SL::DB::Manager::TimeRecording->get_all(...);
65

  
66
    # Add a simple data
67
    my $total = $self->get_total($objects);
68
    push @$objects, make_control_row(
69
      "data",
70
      row => { duration => { data  => $total,
71
                             class => 'listtotal',
72
                             link  => '#info_for_total' } }
73
    );
74

  
75
    # Let report generator create the output.
76
    $self->report_generator_list_objects(
77
      report  => $report,
78
      objects => $objects,
79
    );
80
  }
81

  
82
=head1 PARAMETERS
83

  
84
This control row gets the paramter C<row>, which must a hash ref.
85
The keys are the column names for the fields you want to show your
86
data. The values are hash refs itself and can contain the keys
87
C<raw_data>, C<data>, C<link>, C<class> and C<align> which are passed
88
in the data added to the report.
89

  
90
=head1 AUTHOR
91

  
92
Bernd Bleßmann E<lt>bernd@kivitendo-premium.deE<gt>
93

  
94
=cut
SL/Controller/Helper/ReportGenerator/ControlRow/Separator.pm
1
package SL::Controller::Helper::ReportGenerator::ControlRow::Separator;
2

  
3
use strict;
4

  
5
use parent qw(SL::Controller::Helper::ReportGenerator::ControlRow::Base);
6

  
7

  
8
sub validate_params {
9
  return;
10
}
11

  
12
sub set_data {
13
  my ($self, $report) = @_;
14

  
15
  $report->add_separator();
16
}
17

  
18

  
19
1;
20

  
21

  
22
__END__
23

  
24
=encoding utf-8
25

  
26
=head1 NAME
27

  
28
SL::Controller::Helper::ReportGenerator::ControlRow::Separator - an
29
implementaion of a control row class to display a separator
30

  
31
=head1 DESCRIPTION
32

  
33
This class implements a control row for the report generator helper to display
34
a separator.
35

  
36
=head1 SYNOPSIS
37

  
38
  use SL::Controller::Helper::ReportGenerator;
39
  use SL::Controller::Helper::ReportGenerator::ControlRow qw(make_control_row);
40

  
41
  sub action_list {
42
    my ($self) = @_;
43

  
44
    # Set up the report generator instance. In this example this is
45
    # hidden in "prepare_report".
46
    my $report = $self->prepare_report;
47

  
48
    # Get objects from database.
49
    my $objects = SL::DB::Manager::TimeRecording->get_all(...);
50

  
51
    # Add a separator
52
    push @$objects, make_control_row("separator");
53

  
54
    # Let report generator create the output.
55
    $self->report_generator_list_objects(
56
      report  => $report,
57
      objects => $objects,
58
    );
59
  }
60

  
61
=head1 PARAMETERS
62

  
63
This control row does not use any parameters.
64

  
65
=head1 AUTHOR
66

  
67
Bernd Bleßmann E<lt>bernd@kivitendo-premium.deE<gt>
68

  
69
=cut
SL/Controller/Helper/ReportGenerator/ControlRow/SimpleData.pm
1
package SL::Controller::Helper::ReportGenerator::ControlRow::SimpleData;
2

  
3
use strict;
4

  
5
use parent qw(SL::Controller::Helper::ReportGenerator::ControlRow::Base);
6

  
7

  
8
sub validate_params {
9
  my ($self) = @_;
10

  
11
  my @errors;
12
  push @errors, 'type "simple_data" needs a parameter "data" as hash ref' if !$self->params->{data} || ('HASH' ne ref $self->params->{data});
13

  
14
  return @errors;
15
}
16

  
17
sub set_data {
18
  my ($self, $report) = @_;
19

  
20
  my %data = map {
21
    my $tmp;
22
    $tmp->{data} = $self->params->{data}->{$_};
23
    $_ => $tmp;
24
  } keys %{ $self->params->{data} };
25

  
26
  $report->add_data(\%data);
27
}
28

  
29

  
30
1;
31

  
32

  
33
__END__
34

  
35
=encoding utf-8
36

  
37
=head1 NAME
38

  
39
SL::Controller::Helper::ReportGenerator::ControlRow::SimpleData - an
40
implementaion of a control row class to display simple data
41

  
42
=head1 DESCRIPTION
43

  
44
This class implements a control row for the report generator helper to display
45
simple data. C<Simple> because you only have to provide the column and your data
46
as a string.
47

  
48
=head1 SYNOPSIS
49

  
50
  use SL::Controller::Helper::ReportGenerator;
51
  use SL::Controller::Helper::ReportGenerator::ControlRow qw(make_control_row);
52

  
53
  sub action_list {
54
    my ($self) = @_;
55

  
56
    # Set up the report generator instance. In this example this is
57
    # hidden in "prepare_report".
58
    my $report = $self->prepare_report;
59

  
60
    # Get objects from database.
61
    my $objects = SL::DB::Manager::TimeRecording->get_all(...);
62

  
63
    # Add a simple data
64
    push @$objects, make_control_row(
65
      "simple_data",
66
      data => { duration => 'Total sum of duration is not implemeted yet' }
67
    );
68

  
69
    # Let report generator create the output.
70
    $self->report_generator_list_objects(
71
      report  => $report,
72
      objects => $objects,
73
    );
74
  }
75

  
76
=head1 PARAMETERS
77

  
78
This control row gets the paramter C<data>, which must a hash ref.
79
The keys are the column names for the fields you want to show your
80
data. The values are the data.
81

  
82
=head1 AUTHOR
83

  
84
Bernd Bleßmann E<lt>bernd@kivitendo-premium.deE<gt>
85

  
86
=cut

Auch abrufbar als: Unified diff