Added head_hash method to Project, and some test cleanups.
[catagits/Gitalist.git] / lib / Gitalist / Git / Project.pm
CommitLineData
56b6dbe6 1use MooseX::Declare;
2
3class Gitalist::Git::Project {
4 # FIXME, use Types::Path::Class and coerce
5 use MooseX::Types::Common::String qw/NonEmptySimpleStr/;
6 use DateTime;
7 use Path::Class;
941bb5a1 8 use Gitalist::Git::Util;
56b6dbe6 9
4baaeeef 10 our $SHA1RE = qr/[0-9a-fA-F]{40}/;
11
56b6dbe6 12 has name => ( isa => NonEmptySimpleStr,
13 is => 'ro' );
14 has path => ( isa => "Path::Class::Dir",
15 is => 'ro');
16
17 has description => ( isa => NonEmptySimpleStr,
18 is => 'ro',
19 lazy_build => 1,
20 );
21 has owner => ( isa => NonEmptySimpleStr,
22 is => 'ro',
23 lazy_build => 1,
24 );
25 has last_change => ( isa => 'DateTime',
26 is => 'ro',
27 lazy_build => 1,
28 );
941bb5a1 29 has _util => ( isa => 'Gitalist::Git::Util',
30 is => 'ro',
31 lazy_build => 1,
32 handles => [ 'run_cmd' ],
33 );
56b6dbe6 34
941bb5a1 35 method _build__util {
36 my $util = Gitalist::Git::Util->new(
37 gitdir => $self->path,
38 );
39 return $util;
40 }
56b6dbe6 41
42 method _build_description {
43 my $description = $self->path->file('description')->slurp;
44 chomp $description;
45 return $description;
46 }
47
48 method _build_owner {
49 my $owner = (getpwuid $self->path->stat->uid)[6];
50 $owner =~ s/,+$//;
51 return $owner;
52 }
53
54 method _build_last_change {
55 my $last_change;
56 my $output = $self->run_cmd(
57 qw{ for-each-ref --format=%(committer)
58 --sort=-committerdate --count=1 refs/heads
59 });
60 if (my ($epoch, $tz) = $output =~ /\s(\d+)\s+([+-]\d+)$/) {
61 my $dt = DateTime->from_epoch(epoch => $epoch);
62 $dt->set_time_zone($tz);
63 $last_change = $dt;
64 }
65 return $last_change;
66 }
67
4baaeeef 68=head2 head_hash
69
70Find the hash of a given head (defaults to HEAD).
71
72=cut
73
74 method head_hash (Str $head?) {
75 my $output = $self->run_cmd(qw/rev-parse --verify/, $head || 'HEAD' );
76 return unless defined $output;
77
78 my($sha1) = $output =~ /^($SHA1RE)$/;
79 return $sha1;
80 }
81
56b6dbe6 82 method project_dir (Path::Class::Dir $project) {
83 my $dir = $project->stringify;
84 $dir .= '/.git'
85 if -f dir($dir)->file('.git/HEAD');
86 return $dir;
87 }
88
56b6dbe6 89 # Compatibility
90
91=head2 project_info
92
93Returns a hash containing properties of this project. The keys will
94be:
95
96 name
97 description (empty if .git/description is empty/unnamed)
98 owner
99 last_change
100
101=cut
102
103 method project_info {
104 return {
105 name => $self->name,
106 description => $self->description,
107 owner => $self->owner,
108 last_change => $self->last_change,
109 };
110 };
111
112} # end class