view release on metacpan or search on metacpan
"Thomas Klausner <domm\@plix.at>"
],
"dist_name" => "App-TimeTracker",
"dist_version" => "3.010",
"license" => "perl",
"module_name" => "App::TimeTracker",
"recursive_test_files" => 1,
"requires" => {
"Carp" => 0,
"Data::Dumper" => 0,
"DateTime" => 0,
"DateTime::Format::Duration" => 0,
"DateTime::Format::ISO8601" => 0,
"Exporter" => 0,
"File::Copy" => 0,
"File::Find::Rule" => 0,
"File::HomeDir" => 0,
"Hash::Merge" => 0,
"JSON::XS" => 0,
"Moose" => 0,
"Moose::Role" => 0,
"Moose::Util::TypeConstraints" => 0,
"MooseX::Getopt" => 0,
- squash a warning (cpan-rt75266) (Thomas Klausner)
- fix tag sorting (Jozef Kutej)
- set tracker script STDOUT to utf8 (Jozef Kutej)
- add description to the detail report (Jozef Kutej)
- Switch to Digest::SHA (in core since 5.9.3) to reduce external
deps (Roland Lammel)
2.017 2012-01-12T22:59:32+0100
- finally fixed rt.cpan.org #73859:
During DateTime coercion for --at new DateTime objects
were initiated without setting time_zone => 'local'
That's added now (and tested), so hopefully the bug IS squashed
- new command: version
prints out the current version
- add suggestion for better --at if stop<start
(suggested by Ruslan Zakirov)
2.016 2012-01-10T23:08:20+0100
- fixed rt.cpan.org #73859 reported by Ruslan Zakirov:
make syncing via git et.al. easier
0.08 2008-04-04
- added cmd "report"
- added --this and --last to "worked"
- "worked" now works with tags
- added --from and --to to "worked"
- added --svn to "stop"
- added some docs
- added missing dependency on DateTime::Format::Strptime
0.07 2008-01-23
- added docs
- fixed bad default filepath
0.06 2008-01-22
- renamed to App::TimeTracker
- first release to CPAN
},
"configure" : {
"requires" : {
"Module::Build" : "0.28"
}
},
"runtime" : {
"requires" : {
"Carp" : "0",
"Data::Dumper" : "0",
"DateTime" : "0",
"DateTime::Format::Duration" : "0",
"DateTime::Format::ISO8601" : "0",
"Exporter" : "0",
"File::Copy" : "0",
"File::Find::Rule" : "0",
"File::HomeDir" : "0",
"Hash::Merge" : "0",
"JSON::XS" : "0",
"Moose" : "0",
"Moose::Role" : "0",
"Moose::Util::TypeConstraints" : "0",
"MooseX::Getopt" : "0",
# This file is generated by Dist::Zilla::Plugin::CPANFile v6.024
# Do not edit this file directly. To change prereqs, edit the `dist.ini` file.
requires "Carp" => "0";
requires "Data::Dumper" => "0";
requires "DateTime" => "0";
requires "DateTime::Format::Duration" => "0";
requires "DateTime::Format::ISO8601" => "0";
requires "Exporter" => "0";
requires "File::Copy" => "0";
requires "File::Find::Rule" => "0";
requires "File::HomeDir" => "0";
requires "Hash::Merge" => "0";
requires "JSON::XS" => "0";
requires "Moose" => "0";
requires "Moose::Role" => "0";
requires "Moose::Util::TypeConstraints" => "0";
requires "MooseX::Getopt" => "0";
helper/convert_2_003_to_2_004.pl view on Meta::CPAN
#!/env perl
use strict;
use warnings;
use 5.010;
use File::Find::Rule;
use Data::Dumper;
use App::TimeTracker::Data::Task;
use App::TimeTracker::Proto;
use DateTime;
use Path::Class;
use Try::Tiny;
use JSON::XS;
use Path::Class;
$|=1;
my $app = App::TimeTracker::Proto->new;
my @files = File::Find::Rule->file()->name(qr/\.trc$/)
->in( $app->home );
helper/convert_legacy_data_to_json.pl view on Meta::CPAN
#!/env perl
use strict;
use warnings;
use 5.010;
use File::Find::Rule;
use Data::Dumper;
use App::TimeTracker::Data::Task;
use DateTime;
use Path::Class;
use Try::Tiny;
$|=1;
my ($in, $out) = @ARGV;
die "please specify dir containing old-style files" unless -d $in;
die "please specify dir to contain new-style files" unless -d $out;
$out = Path::Class::dir($out);
my @files = File::Find::Rule->file()->name(qr/\.(done|current)$/)
helper/convert_legacy_data_to_json.pl view on Meta::CPAN
}
my @tags;
if ($data{tags}) {
foreach (split(/\s+/,$data{tags})) {
push(@tags,$_);
}
}
my $task = App::TimeTracker::Data::Task->new({
start=>DateTime->from_epoch(epoch=>$data{start}, time_zone=>'local'),
stop=>DateTime->from_epoch(epoch=>$data{stop}, time_zone=>'local'),
project=>$data{project},
tags=>\@tags,
});
$task->save($out);
print '.';
}
catch {
die "An error occurred converting $old";
}
lib/App/TimeTracker.pm view on Meta::CPAN
package App::TimeTracker;
# ABSTRACT: time tracking for impatient and lazy command line lovers
our $VERSION = '3.010'; # VERSION
use strict;
use warnings;
use 5.010;
use App::TimeTracker::Data::Task;
use DateTime;
use Moose;
use Moose::Util::TypeConstraints;
use Path::Class qw();
use Path::Class::Iterator;
use MooseX::Storage::Format::JSONpm;
use JSON::XS;
our $HOUR_RE = qr/(?<hour>[012]?\d)/;
our $MINUTE_RE = qr/(?<minute>[0-5]?\d)/;
our $DAY_RE = qr/(?<day>[0123]?\d)/;
our $MONTH_RE = qr/(?<month>[01]?\d)/;
our $YEAR_RE = qr/(?<year>2\d{3})/;
with qw(
MooseX::Getopt
);
subtype 'TT::DateTime' => as class_type('DateTime');
subtype 'TT::RT' => as 'Int';
subtype 'TT::Duration' => as enum( [qw(day week month year)] );
coerce 'TT::RT' => from 'Str' => via {
my $raw = $_;
$raw =~ s/\D//g;
return $raw;
};
coerce 'TT::DateTime' => from 'Str' => via {
my $raw = $_;
my $dt = DateTime->now;
$dt->set_time_zone('local');
$dt->set( second => 0 );
if ($raw) {
if ( $raw =~ /^ $HOUR_RE : $MINUTE_RE $/x ) { # "13:42"
$dt->set( hour => $+{hour}, minute => $+{minute} );
}
elsif ( $raw =~ /^ $YEAR_RE [-.]? $MONTH_RE [-.]? $DAY_RE $/x )
{ # "2010-02-26"
$dt->set( year => $+{year}, month => $+{month}, day => $+{day} );
lib/App/TimeTracker.pm view on Meta::CPAN
hour => $+{hour},
minute => $+{minute} );
}
else {
confess "Invalid date format '$raw'";
}
}
return $dt;
};
MooseX::Getopt::OptionTypeMap->add_option_type_to_map( 'TT::DateTime' => '=s',
);
MooseX::Getopt::OptionTypeMap->add_option_type_to_map( 'TT::RT' => '=i', );
no Moose::Util::TypeConstraints;
has 'home' => (
is => 'ro',
isa => 'Path::Class::Dir',
traits => ['NoGetopt'],
required => 1,
lib/App/TimeTracker.pm view on Meta::CPAN
my $self = shift;
my $command = 'cmd_' . ( $self->extra_argv->[0] || 'missing' );
$self->cmd_commands()
unless $self->can($command);
$self->_current_command($command);
$self->$command;
}
sub now {
my $dt = DateTime->now();
$dt->set_time_zone('local');
return $dt;
}
sub beautify_seconds {
my ( $self, $s ) = @_;
return '0' unless $s;
my ( $m, $h ) = ( 0, 0 );
if ( $s >= 60 ) {
lib/App/TimeTracker/Command/Core.pm view on Meta::CPAN
use 5.010;
use Moose::Role;
use Moose::Util::TypeConstraints;
use App::TimeTracker::Utils qw(now pretty_date error_message);
use App::TimeTracker::Constants qw(MISSING_PROJECT_HELP_MSG);
use File::Copy qw(move);
use File::Find::Rule;
use Data::Dumper;
use Text::Table;
use DateTime;
sub cmd_start {
my $self = shift;
unless ( $self->has_current_project ) {
error_message( MISSING_PROJECT_HELP_MSG );
exit;
}
$self->cmd_stop('no_exit');
lib/App/TimeTracker/Command/Core.pm view on Meta::CPAN
if ($parent) {
unshift( @$ancestors, $parent );
$self->_get_ancestors( $report, $projects, $parent, $ancestors );
}
}
sub _first_day_of_week {
my ( $self, $year, $week ) = @_;
# Week 1 is defined as the one containing January 4:
return DateTime->new( year => $year, month => 1, day => 4 )
->add( weeks => ( $week - 1 ) )->truncate( to => 'week' );
}
sub _print_report_tree {
my ( $self, $report, $projects, $project, $padding, $tagpadding ) = @_;
my $data = $report->{$project};
my $sum = 0;
$sum += $data->{'_total'} if $data->{'_total'};
$sum += $data->{'_kids'} if $data->{'_kids'};
lib/App/TimeTracker/Command/Core.pm view on Meta::CPAN
say "\t$command";
}
}
exit;
}
sub _load_attribs_worked {
my ( $class, $meta ) = @_;
$meta->add_attribute(
'from' => {
isa => 'TT::DateTime',
is => 'ro',
coerce => 1,
lazy_build => 1,
#cmd_aliases => [qw/start/],
documentation => 'Beginning of time period to report',
}
);
$meta->add_attribute(
'to' => {
isa => 'TT::DateTime',
is => 'ro',
coerce => 1,
#cmd_aliases => [qw/end/],
lazy_build => 1,
documentation => 'End of time period to report',
}
);
$meta->add_attribute(
'this' => {
lib/App/TimeTracker/Command/Core.pm view on Meta::CPAN
default => 'project',
documentation => 'Genereta Report by week or project.'
}
);
}
sub _load_attribs_start {
my ( $class, $meta ) = @_;
$meta->add_attribute(
'at' => {
isa => 'TT::DateTime',
is => 'ro',
coerce => 1,
documentation => 'Start at',
}
);
$meta->add_attribute(
'project' => {
isa => 'Str',
is => 'ro',
documentation => 'Project name',
lib/App/TimeTracker/Command/Core.pm view on Meta::CPAN
=head2 start
~/perl/Your-Project$ tracker start
Started working on Your-Project at 23:44:19
Start tracking the current project now. Automatically stop the previous task, if there was one.
=head3 Options:
=head4 --at TT::DateTime
~/perl/Your-Project$ tracker start --at 12:42
~/perl/Your-Project$ tracker start --at '2011-02-26 12:42'
Start at the specified time/datetime instead of now. If only a time is
provided, the day defaults to today. See L<TT::DateTime> in L<App::TimeTracker>.
=head4 --project SomeProject
~/perl/Your-Project$ tracker start --project SomeProject
Use the specified project instead of the one determined by the current
working directory.
=head4 --description 'some prosa'
lib/App/TimeTracker/Command/Core.pm view on Meta::CPAN
=head2 stop
~/perl/Your-Project$ tracker stop
Worked 00:20:50 on Your-Project
Stop tracking the current project now.
=head3 Options
=head4 --at TT::DateTime
Stop at the specified time/datetime instead of now.
=head2 continue
~/perl/Your-Project$ tracker continue
Continue working on the previous task after a break.
Example:
lib/App/TimeTracker/Command/Core.pm view on Meta::CPAN
=head2 worked
~/perl/Your-Project$ tracker worked [SPAN]
Report the total time worked in the given time span, maybe limited to
some projects.
=head3 Options:
=head4 --from TT::DateTime [REQUIRED (or use --this/--last)]
Begin of reporting interval, defaults to first day of current month.
=head4 --to TT::DateTime [REQUIRED (or use --this/--last)]
End of reporting interval, default to DateTime->now.
=head4 --this [day, week, month, year]
Automatically set C<--from> and C<--to> to the calculated values
~/perl/Your-Project$ tracker worked --this week
17:01:50
=head4 --last [day, week, month, year]
lib/App/TimeTracker/Data/Task.pm view on Meta::CPAN
# ABSTRACT: App::TimeTracker Task storage
our $VERSION = '3.010'; # VERSION
use 5.010;
use Moose;
use App::TimeTracker::Utils qw(now);
use namespace::autoclean;
use App::TimeTracker;
use DateTime::Format::ISO8601;
use DateTime::Format::Duration;
use User::pwent;
use MooseX::Storage;
with Storage(
format => [ JSONpm => { json_opts => { pretty => 1, canonical => 1 } } ],
io => "File",
);
MooseX::Storage::Engine->add_custom_type_handler(
'DateTime' => (
expand => sub { DateTime::Format::ISO8601->parse_datetime(shift) },
collapse => sub { (shift)->iso8601 } ) );
my $dtf_dur = DateTime::Format::Duration->new( pattern => '%H:%M:%S',
normalise => 1 );
my $dtf_sec = DateTime::Format::Duration->new( pattern => '%s' );
has 'start' => (
isa => 'DateTime',
is => 'ro',
required => 1,
default => sub { now() } );
has 'stop' => (
isa => 'DateTime',
is => 'rw',
trigger => \&_calc_duration,
);
has 'seconds' => (
isa => 'Maybe[Int]',
is => 'rw',
lazy_build => 1,
);
sub _build_seconds {
lib/App/TimeTracker/Utils.pm view on Meta::CPAN
print color $color;
print $string;
say color 'reset';
}
sub pretty_date {
my ($date) = @_;
unless ( blessed $date
&& $date->isa('DateTime') )
{
return $date;
}
else {
my $now = now();
my $yesterday = now()->subtract( days => 1 );
if ( $date->dmy eq $now->dmy ) {
return $date->hms(':');
}
elsif ( $date->dmy eq $yesterday->dmy ) {
return 'yesterday ' . $date->hms(':');
}
else {
return $date->dmy('.') . ' ' . $date->hms(':');
}
}
}
sub now {
my $dt = DateTime->now();
$dt->set_time_zone('local');
return $dt;
}
1;
__END__
=pod
=encoding UTF-8
t/Command/core.t view on Meta::CPAN
use App::TimeTracker::Proto;
local $ENV{TZ} = 'UTC';
my $tmp = testlib::Fixtures::setup_tempdir;
my $home = $tmp->subdir('.TimeTracker');
$tmp->subdir('some_project')->mkpath;
$tmp->subdir('other_project')->mkpath;
$tmp->subdir('project_name_auto')->mkpath;
$tmp->subdir('project_name_custom')->mkpath;
my $p = App::TimeTracker::Proto->new( home => $home );
my $now = DateTime->now;
$now->set_time_zone('local');
my $basetf = $now->ymd('') . '-';
my $tracker_dir = $home->subdir( $now->year, sprintf( "%02d", $now->month ) );
{ # init
@ARGV = ('init');
my $class = $p->setup_class( {} );
file_exists_ok( $home->file('projects.json') );
file_exists_ok( $home->file('tracker.json') );
t/Command/rt_73859_daychange.t view on Meta::CPAN
use 5.010;
use strict;
use warnings;
use lib qw(t);
use Test::MockTime qw(); # this needs to be loaded before DateTime
# http://www.nntp.perl.org/group/perl.datetime/2008/08/msg7043.html
use Test::Most;
use Test::Trap;
use Test::File;
use testlib::FakeHomeDir;
use App::TimeTracker::Proto;
use DateTime;
local $ENV{TZ} = 'UTC';
my $tmp = testlib::Fixtures::setup_tempdir;
my $home = $tmp->subdir('.TimeTracker');
my $prjdir = $tmp->subdir('rt73859');
$home->mkpath;
$prjdir->mkpath;
$home->file('projects.json')
->spew( iomode => '>:encoding(UTF-8)', '{"rt73859":"' . $prjdir . '"}' . "\n" );
$prjdir->file('.tracker.json')->spew( iomode => '>:encoding(UTF-8)', '{}' . "\n" );
t/Command/rt_73859_daychange.t view on Meta::CPAN
my $p = App::TimeTracker::Proto->new( home => $home, project => 'rt73859' );
$p->load_config( $home, 'rt73859' );
my $tracker_dir = $home->subdir( '2012', '01' );
my $c = { project => 'rt73859' };
# test what was reported, but it works
diag("Test initial bug report");
{ # start
my $test_date =
DateTime->new( year => 2012, month => 1, day => 9, hour => 21, time_zone => 'local' );
Test::MockTime::set_fixed_time( $test_date->epoch );
@ARGV = ('start');
my $class = $p->setup_class($c);
my $t = $class->name->new(
home => $home,
config => $c,
_current_project => 'rt73859',
at => '23:30'
);
trap { $t->cmd_start };
is( $trap->stdout, "Started working on rt73859 at 23:30:00\n", 'start: output' );
file_not_empty_ok( $tracker_dir->file('20120109-233000_rt73859.trc'), 'tracker file exists' );
}
{ # stop
my $test_date = DateTime->new(
year => 2012,
month => 1,
day => 10,
hour => '00',
minute => 3,
time_zone => 'local'
);
Test::MockTime::set_fixed_time( $test_date->epoch );
@ARGV = ('stop');
t/Command/rt_73859_daychange.t view on Meta::CPAN
is( $task->seconds, 60 * 60, 'task: seconds' );
is( $task->duration, '01:00:00', 'task: duration' );
}
# ah, I assume there is a different bug:
# if you issue 'tracker stop --at 00:10' but it is 23:59, the stop-time will be set for the current day, i.e. way before the start time
# solution do not allow to set stop times that are before the start time.
diag("Test de facto bug");
{ # start
my $test_date = DateTime->new(
year => 2012,
month => 1,
day => 8,
hour => 23,
minute => 30,
time_zone => 'local'
);
Test::MockTime::set_fixed_time( $test_date->epoch );
@ARGV = ('start');
my $class = $p->setup_class($c);
my $t = $class->name->new( home => $home, config => $c, _current_project => 'rt73859' );
trap { $t->cmd_start };
is( $trap->stdout, "Started working on rt73859 at 23:30:00\n", 'start: output' );
file_not_empty_ok( $tracker_dir->file('20120108-233000_rt73859.trc'), 'tracker file exists' );
}
{ # stop
my $test_date = DateTime->new(
year => 2012,
month => 1,
day => 8,
hour => 23,
minute => 45,
time_zone => 'local'
);
Test::MockTime::set_fixed_time( $test_date->epoch );
@ARGV = ('stop');
t/Command/rt_73859_daychange.t view on Meta::CPAN
trap { $t->cmd_stop };
like( $trap->stdout, qr/This makes no sense/, 'stop: aborted output' );
my $task = App::TimeTracker::Data::Task->load(
$tracker_dir->file('20120108-233000_rt73859.trc')->stringify );
is( $task->stop, undef, 'task: no stop time' );
file_not_empty_ok( $home->file('current'), '"current" file still exists' );
}
{ # stop again, with long --at
my $test_date = DateTime->new(
year => 2012,
month => 1,
day => 8,
hour => 23,
minute => 45,
time_zone => 'local'
);
Test::MockTime::set_fixed_time( $test_date->epoch );
@ARGV = ('stop');
t/Task/helpers.t view on Meta::CPAN
use 5.010;
use strict;
use warnings;
use lib 't';
use Test::Most;
use DateTime;
use App::TimeTracker::Data::Task;
{ # _calc_duration, rounded_minutes
my $task = App::TimeTracker::Data::Task->new(
{ project => 'test',
start => DateTime->new(
year => 2010,
month => 2,
day => 26,
hour => 10,
minute => 5,
second => 42
),
description =>
'Some Test Task described in a very long sentence that will be probably be shortend',
}
);
my $stop = DateTime->new(
year => 2010,
month => 2,
day => 26,
hour => 12,
minute => 25,
second => 13
);
$task->_calc_duration($stop);
is( $task->seconds, '8371', '_calc_duration: seconds' );
is( $task->duration, '02:19:31', '_calc_duration: duration' );
t/Task/helpers.t view on Meta::CPAN
is( $task->seconds, '11971', '_calc_duration: seconds' );
is( $task->duration, '03:19:31', '_calc_duration: duration' );
is( $task->rounded_minutes, 200, 'rounded_minutes' );
is( $task->description_short, 'Some Test Task described in a very long sentence...',
'description_short' );
}
{ # rounded_minutes
my $task = App::TimeTracker::Data::Task->new(
{ project => 'test',
start => DateTime->new(
year => 2010,
month => 2,
day => 26,
hour => 10,
minute => 5,
second => 0
),
description => 'Worked exactly 15 minutes',
}
);
my $stop = DateTime->new(
year => 2010,
month => 2,
day => 26,
hour => 10,
minute => 20,
second => 0
);
$task->_calc_duration($stop);
is( $task->duration, '00:15:00', 'task duration is 15 minutes' );
is( $task->rounded_minutes, 15, 'rounded_minutes' );
t/Task/start.t view on Meta::CPAN
use testlib::Fixtures;
use App::TimeTracker::Data::Task;
local $ENV{TZ} = 'UTC';
my $capture = IO::Capture::Stdout->new();
my $tmp = testlib::Fixtures::setup_tempdir;
{
my $task = App::TimeTracker::Data::Task->new(
{ project => 'test',
start => DateTime->new(
year => 2010,
month => 2,
day => 26,
hour => 10,
minute => 5,
second => 42
),
}
);
t/Task/storage_location.t view on Meta::CPAN
use 5.010;
use strict;
use warnings;
use lib 't';
use Test::Most;
use testlib::Fixtures;
use DateTime;
use App::TimeTracker::Data::Task;
my $tmp = testlib::Fixtures::setup_tempdir;
{
my $task = App::TimeTracker::Data::Task->new(
{ project => 'test',
start => DateTime->new(
year => 2010,
month => 2,
day => 26,
hour => 10,
minute => 5,
second => 42
),
}
);
t/TimeTracker/datetime_coerce.t view on Meta::CPAN
use Test::Most;
use App::TimeTracker;
use testlib::Fixtures;
my $tmp = testlib::Fixtures::setup_tempdir;
package ThisTest;
use Moose;
extends 'App::TimeTracker';
has 'dt' => (
isa => 'TT::DateTime',
is => 'ro',
coerce => 1,
);
package main;
local $ENV{TZ} = 'UTC';
my $now = DateTime->now;
$now->set_time_zone('local');
my $date = DateTime->new( year => 2012, month => 2, day => 26, time_zone => 'UTC' );
foreach my $test (
[ '12:34', $now->clone->set( hour => 12, minute => 34, second => 0 ) ],
[ '0:1', $now->clone->set( hour => 0, minute => 1, second => 0 ) ],
[ '2012-02-26', $date->clone ],
[ '2012-02-26 12:34', $date->clone->set( hour => 12, minute => 34, second => 0 ) ],
# for our crazy American friends...
[ '26-02-2012', $date->clone ],
[ '26-02-2012 12:34', $date->clone->set( hour => 12, minute => 34, second => 0 ) ],
t/TimeTracker/find_task_files.t view on Meta::CPAN
use 5.010;
use strict;
use warnings;
use lib 't';
use Test::Most;
use testlib::Fixtures;
use DateTime;
use App::TimeTracker;
local $ENV{TZ} = 'UTC';
my $tmp = testlib::Fixtures->setup_2011_05;
my $t = App::TimeTracker->new( home => $tmp, config => {} );
{
my @files = $t->find_task_files(
{ from => DateTime->new( year => '2011', month => 5, day => 20 ),
to => DateTime->new( year => '2011', month => 5, day => 25 ),
}
);
is( scalar @files, 6, 'got 6 files' );
is( $files[0], $tmp->file( '2011', '05', '20110520-093423_oe1_orf_at.trc' ), 'first file' );
is( $files[5], $tmp->file( '2011', '05', '20110525-224324_App_TimeTracker.trc' ), 'last file' );
}
{
my @files = $t->find_task_files( { projects => ['TimeTracker'], } );
is( scalar @files, 7, 'got 7 files' );
is( ( scalar grep {/App_TimeTracker/} @files ), 7, 'all match project' );
}
{
my @files = $t->find_task_files(
{ from => DateTime->new( year => '2011', month => 5, day => 1 ),
projects => ['oe1'],
}
);
is( scalar @files, 16, 'got 16 files' );
}
done_testing();
t/TimeTracker/helpers.t view on Meta::CPAN
use 5.010;
use strict;
use warnings;
use lib 't';
use Test::Most;
use testlib::Fixtures;
use DateTime;
use App::TimeTracker;
my $tmp = testlib::Fixtures::setup_tempdir;
local $ENV{TZ} = 'UTC';
my %BASE = ( home => $tmp, config => {} );
{ # $self->now
my $exp = DateTime->now( time_zone => 'local' );
my $got = App::TimeTracker->now;
is( $exp->ymd, $got->ymd, '$self->now: ymd' );
is( $exp->strftime('%H:%M'), $got->strftime('%H:%M'), '$self->now: hh:mm' );
}
{ # beautify_seconds
my @tests = (
[ undef, '0' ],
[ '0', '0' ],
[ '59', '00:00:59' ],
t/TimeTracker/helpers.t view on Meta::CPAN
{ # to / from
my $class = Moose::Meta::Class->create_anon_class(
superclasses => ['App::TimeTracker'],
roles => ['App::TimeTracker::Command::Core'],
);
my $class_name = $class->name;
$class_name->_load_attribs_worked($class);
no warnings 'redefine';
local *DateTime::now =
sub { return DateTime->new( year => 2011, month => 9, day => 7, hour => 12 ) };
{
my $t1 = $class_name->new( { %BASE, this => 'week', } );
is( $t1->from->iso8601, '2011-09-05T00:00:00', 'From 1 ok' );
is( $t1->to->iso8601, '2011-09-11T23:59:59', 'To 1 ok' );
}
{
my $t2 = $class_name->new( { %BASE, last => 'week', } );