Projekt

Allgemein

Profil

« Zurück | Weiter » 

Revision 81be8de1

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

  • ID 81be8de172fbced49cbcfe5f4d7a76b2c1c0585f
  • Vorgänger 9e41b7f3
  • Nachfolger 3acdb292

Zeiterfassung: Controller

Unterschiede anzeigen:

SL/DB/TimeRecording.pm
5 5

  
6 6
use strict;
7 7

  
8
use SL::Locale::String qw(t8);
9

  
10
use SL::DB::Helper::AttrDuration;
11
use SL::DB::Helper::AttrHTML;
12

  
8 13
use SL::DB::MetaSetup::TimeRecording;
9 14
use SL::DB::Manager::TimeRecording;
10 15

  
11 16
__PACKAGE__->meta->initialize;
12 17

  
18
__PACKAGE__->attr_duration_minutes(qw(duration));
19

  
20
__PACKAGE__->attr_html('description');
21

  
22
__PACKAGE__->before_save('_before_save_check_valid');
23

  
24
sub _before_save_check_valid {
25
  my ($self) = @_;
26

  
27
  my @errors = $self->validate;
28
  return (scalar @errors == 0);
29
}
30

  
31
sub validate {
32
  my ($self) = @_;
33

  
34
  my @errors;
35

  
36
  push @errors, t8('Start time must not be empty.')                            if !$self->start_time;
37
  push @errors, t8('Customer must not be empty.')                              if !$self->customer_id;
38
  push @errors, t8('Staff member must not be empty.')                          if !$self->staff_member_id;
39
  push @errors, t8('Employee must not be empty.')                              if !$self->employee_id;
40
  push @errors, t8('Description must not be empty.')                           if !$self->description;
41
  push @errors, t8('Start time must be earlier than end time.')                if $self->is_time_in_wrong_order;
42

  
43
  my $conflict = $self->is_time_overlapping;
44
  push @errors, t8('Entry overlaps with "#1".', $conflict->displayable_times)  if $conflict;
45

  
46
  return @errors;
47
}
48

  
49
sub is_time_overlapping {
50
  my ($self) = @_;
51

  
52
  # Do not allow overlapping time periods.
53
  # Start time can be equal to another end time
54
  # (an end time can be equal to another start time)
55

  
56
  # We cannot check if no staff member is given.
57
  return if !$self->staff_member_id;
58

  
59
  # If no start time and no end time are given, there is no overlapping.
60
  return if !($self->start_time || $self->end_time);
61

  
62
  my $conflicting;
63

  
64
  # Start time or end time can be undefined.
65
  if (!$self->start_time) {
66
    $conflicting = SL::DB::Manager::TimeRecording->get_all(where  => [ and => [ '!id'           => $self->id,
67
                                                                                staff_member_id => $self->staff_member_id,
68
                                                                                start_time      => {lt => $self->end_time},
69
                                                                                end_time        => {ge => $self->end_time} ] ],
70
                                                           sort_by => 'start_time DESC',
71
                                                           limit   => 1);
72
  } elsif (!$self->end_time) {
73
    $conflicting = SL::DB::Manager::TimeRecording->get_all(where  => [ and => [ '!id'           => $self->id,
74
                                                                                staff_member_id => $self->staff_member_id,
75
                                                                                or              => [ and => [start_time => {le => $self->start_time},
76
                                                                                                             end_time   => {gt => $self->start_time} ],
77
                                                                                                     start_time => $self->start_time,
78
                                                                                ],
79
                                                                       ],
80
                                                           ],
81
                                                           sort_by => 'start_time DESC',
82
                                                           limit   => 1);
83
  } else {
84
    $conflicting = SL::DB::Manager::TimeRecording->get_all(where  => [ and => [ '!id'           => $self->id,
85
                                                                                staff_member_id => $self->staff_member_id,
86
                                                                                or              => [ and => [ start_time => {lt => $self->end_time},
87
                                                                                                              end_time   => {gt => $self->start_time} ] ,
88
                                                                                                     or  => [ start_time => $self->start_time,
89
                                                                                                              end_time   => $self->end_time, ],
90
                                                                                ]
91
                                                                       ]
92
                                                           ],
93
                                                           sort_by => 'start_time DESC',
94
                                                           limit   => 1);
95
  }
96

  
97
  return $conflicting->[0] if @$conflicting;
98
  return;
99
}
100

  
101
sub is_time_in_wrong_order {
102
  my ($self) = @_;
103

  
104
  if ($self->start_time && $self->end_time
105
      && $self->start_time >= $self->end_time) {
106
    return 1;
107
  }
108

  
109
  return;
110
}
111

  
112
sub displayable_times {
113
  my ($self) = @_;
114

  
115
  # placeholder
116
  my $ph = $::locale->format_date_object(DateTime->new(year => 1111, month => 11, day => 11, hour => 11, minute => 11), precision => 'minute');
117
  $ph =~ s{1}{-}g;
118

  
119
  return ($self->start_time_as_timestamp||$ph) . ' - ' . ($self->end_time_as_timestamp||$ph);
120
}
121

  
122
sub duration {
123
  my ($self) = @_;
124

  
125
  if ($self->start_time && $self->end_time) {
126
    return ($self->end_time->subtract_datetime_absolute($self->start_time))->seconds/60.0;
127
  } else {
128
    return;
129
  }
130
}
131

  
13 132
1;

Auch abrufbar als: Unified diff