view lib/Benzin/Bugzilla/Bug.pm @ 11:4eb9fdf4efa9

refactoring, non-working bookings
author cin
date Mon, 07 Sep 2015 19:18:21 +0300
parents 14a966369278
children 52b34ea50eff
line wrap: on
line source

package Benzin::Bugzilla::Bug;
use strict;
use POSIX;
use Scalar::Util qw(looks_like_number);
use DateTime;

my @fields;

BEGIN {
	@fields = qw(
	  id
	  summary
	  creation_time
	  last_change_time
	  creator
	  assigned_to
	  qa_contact
	  cc

	  is_open
	  status
	  resolution

	  priority
	  severity
	  url

	  blocks
	  depends_on

	  component
	  product
	  classification
	  version

	  actual_time
	  estimated_time
	  remaining_time
	  deadline

	  comments
	  history
	);
}

use constant { BUG_FIELDS => \@fields };

use IMPL::declare { base => [ 'IMPL::Object::Fields' => undef ] };
use fields @fields;

sub CTOR {
	my SELF $this = shift;
	my $data = shift;
	$this->{$_} = $data->{$_}
	  foreach grep exists $data->{$_}, @{ SELF->BUG_FIELDS };
}

# returns {
#	reports => [
#		{ who => email:string, start => work-start-date-time:DateTime, end => report-date-time:DateTime, work_time => hours:double }
#	],
#   actual => hours
#	remaining => hours
# }
sub GetTimeReports {
	my SELF $this = shift;
	my $resolution = shift || 0.25;
	my $span = $resolution * 60;

	my @bookings;
	my $actual = 0;

	for my $history ( @{ $this->{history} || [] } ) {
		my $who     = $history->{who};
		my $when    = $history->{when};
		my $changes = $history->{changes};
		
		my $minutes = coarsen( $when->minute(), $span );
		
		if ($minutes >= 60 ) {
			$when->add(hours => 1);
			$minutes -= 60;
		}
		$when->set_second(0);
		$when->set_minute($minutes);
		

		for my $change ( @{ $changes || [] } ) {
			if ( $change->{field_name} eq 'work_time' ) {
				my $prev  = $change->{removed} || 0;
				my $value = $change->{added}   || 0;
				if ( looks_like_number($prev) and looks_like_number($value) ) {
					my $dt = coarsen( $value - $prev, $resolution );

					if ($dt) {
						push @bookings,
						  {
							who       => $who,
							end      => $when,
							work_time => $dt,
							start => $when->clone()->subtract( hours => $dt )
						  };
						$actual += $dt;
					}
				}
			}
		}
	}

	my $remaining = coarsen( $this->{remaining_time}, $resolution );
	return {
		report    => \@bookings,
		actual    => $actual,
		remaining => $remaining,
		estimated => $actual + $remaining
	};
}

sub coarsen {
	my ( $value, $resolution ) = @_;
	return $resolution ? ceil( $value / $resolution ) * $resolution : $value;
}

1;