Add some filesystem access functions to CIL::VCS::*
authorSam Vilain <sam.vilain@catalyst.net.nz>
Wed, 16 Jul 2008 05:36:43 +0000 (17:36 +1200)
committerSam Vilain <sam.vilain@catalyst.net.nz>
Wed, 16 Jul 2008 05:36:43 +0000 (17:36 +1200)
lib/CIL/VCS/Factory.pm
lib/CIL/VCS/Git.pm

index ec5da5378e34d02be64e1af17758ba9a35edff35..52ac43ed7b7e69532754b32408648b1e54d3f694 100644 (file)
@@ -30,7 +30,7 @@ use base qw( Class::Factory );
 __PACKAGE__->register_factory_type( Null => 'CIL::VCS::Null' );
 __PACKAGE__->register_factory_type( Git => 'CIL::VCS::Git' );
 
-foreach my $method_name ( qw(post_add) ) {
+foreach my $method_name ( qw(post_add glob_rev file_exists dir_exists get_fh) ) {
     my $method = sub {
         my ($self) = @_;
         my $class = ref $self || $self;
index e4a828678d8d084e175d24d81151743da24bcc5b..3a6f97c78d6fa68412343e40c8d7d18fe05fd474 100644 (file)
@@ -39,6 +39,52 @@ sub post_add {
     return [ "git add @files" ];
 }
 
+use Git;
+
+sub git {
+    my $self = shift;
+    $self->{git} ||= Git->repository;
+}
+
+sub glob_rev {
+    my ($self, $rev, $path) = @_;
+
+    # only support globbing the last element
+    my ($dir, $pattern) = $path =~ m{^([^\*]*/)([^/]*)$}
+           or croak "unsupported pattern '$path'";
+    $pattern =~ s{([\\\.])}{\\$1}g;
+    $pattern =~ s{\*}{.*}g;
+    my @match;
+    $DB::single = 1;
+    for ( $self->git->command("ls-tree", $rev, $dir) ) {
+        chomp;
+        my ($blobid, $path) = m{([0-9a-f]{40})\s+(.*)} or die;
+       if ( $path =~ m{^\Q$dir\E$pattern$} ) {
+           push @match, $path;
+       }
+    }
+    @match;
+}
+
+sub file_exists {
+    my ($self, $rev, $path) = @_;
+
+    my $output = eval { $self->git->command("cat-file", "-t", "$rev:$path") };
+    return ( $output && $output =~ /blob/ );
+}
+
+sub dir_exists {
+    my ($self, $rev, $path) = @_;
+
+    my $output = eval { $self->git->command("cat-file", "-t", "$rev:$path") };
+    return ( $output && $output =~ /tree/ );
+}
+
+sub get_fh {
+    my ($self, $rev, $path) = @_;
+    $self->git->command_output_pipe("cat-file", "blob", "$rev:$path");
+}
+
 ## ----------------------------------------------------------------------------
 1;
 ## ----------------------------------------------------------------------------