[Bps-public-commit] r9032 - in SVN-Hook: lib/SVN/Hook t
clkao at bestpractical.com
clkao at bestpractical.com
Thu Sep 13 09:05:00 EDT 2007
Author: clkao
Date: Thu Sep 13 09:05:00 2007
New Revision: 9032
Added:
SVN-Hook/lib/SVN/Hook/Redispatch.pm
SVN-Hook/t/02partial.t
Modified:
SVN-Hook/lib/SVN/Hook.pm
Log:
library and tests for a redispatch hook.
Modified: SVN-Hook/lib/SVN/Hook.pm
==============================================================================
--- SVN-Hook/lib/SVN/Hook.pm (original)
+++ SVN-Hook/lib/SVN/Hook.pm Thu Sep 13 09:05:00 2007
@@ -59,20 +59,25 @@
sub init {
my ($self, $hook) = @_;
my $path = $self->hook_path($hook);
- die if -e $path;
- open my $fh, '>', $path or die $!;
- my $perl = _this_perl();
- print $fh <<"EOF";
-#!$perl
+ die "There is already $hook file.\n" if -e $path;
+
+ $self->_install_perl_hook( $path, <<"EOF");
# DO NOT EDIT. generated by svnhook version $VERSION.
use SVN::Hook::CLI; SVN::Hook::CLI->_run("$hook", \@ARGV);
EOF
- close $fh;
- chmod 0755, $path or die $!;
mkdir catfile($self->repospath, 'hooks', "_$hook") or die $!;
}
+sub _install_perl_hook {
+ my ($self, $hook_file, $perl_code) = @_;
+ my $perl = _this_perl();
+ open my $fh, '>', $hook_file or die "$hook_file: $!";
+ print $fh "#!$perl\n$perl_code";
+ close $fh;
+ chmod 0755, $hook_file or die $!;
+}
+
sub scripts {
my ( $self, $hook ) = @_;
SVN::Hook::Script->load_from_dir($self->hook_path("_$hook"));
Added: SVN-Hook/lib/SVN/Hook/Redispatch.pm
==============================================================================
--- (empty file)
+++ SVN-Hook/lib/SVN/Hook/Redispatch.pm Thu Sep 13 09:05:00 2007
@@ -0,0 +1,62 @@
+package SVN::Hook::Redispatch;
+use strict;
+use Data::Dumper;
+use Path::Class;
+use SVN::Hook;
+
+sub import {
+ my $class = shift;
+ my $spec = shift;
+
+ my $hook_base = Path::Class::File->new($0)->parent;
+
+ my $type;
+ my $svnlook_arg;
+ if ($hook_base =~ m/pre-commit$/) {
+ $type = 'pre-commit';
+ $svnlook_arg = "-t $_[1]";
+ }
+ elsif ($hook_base =~ m/post-commit$/) {
+ $type = 'post-commit';
+ $svnlook_arg = "-r $_[1]";
+ }
+ else {
+ die "not yet";
+ }
+
+ my $toplevel = $class->find_toplevel_change($_[0], $svnlook_arg);
+
+ for (map { Path::Class::Dir->new_foreign('Unix', $_) } sort keys %$spec) {
+ next unless $_ eq $toplevel || $_->subsumes($toplevel);
+ my @scripts = SVN::Hook::Script->load_from_dir
+ ( $hook_base.'/'.$spec->{$_} );
+ SVN::Hook->run_scripts( \@scripts );
+ }
+
+};
+
+sub find_toplevel_change {
+ my $class = shift;
+ my $repos = shift;
+ my $arg = shift;
+
+ my $svnlook = '/usr/local/bin/svnlook';
+ open my $fh, '-|', "$svnlook dirs-changed $arg $repos"
+ or die "Unable to run svnlook: $!";
+ my $toplevel;
+ while (<$fh>) {
+ chomp;
+ if (!$toplevel) {
+ $toplevel = Path::Class::Dir->new_foreign('Unix', $_);
+ }
+ else {
+ while (!$toplevel->subsumes($_)) {
+ $toplevel = $toplevel->parent;
+ }
+
+ }
+ }
+ return $toplevel;
+}
+
+1;
Added: SVN-Hook/t/02partial.t
==============================================================================
--- (empty file)
+++ SVN-Hook/t/02partial.t Thu Sep 13 09:05:00 2007
@@ -0,0 +1,50 @@
+#!/usr/bin/perl -w
+
+use Test::More;
+eval { use SVK::Test; 1 }
+ or plan skip_all => 'requires SVK for testing.';
+
+plan tests => 4;
+use_ok('SVN::Hook');
+use File::Temp 'tempdir';
+use File::Path 'mkpath';
+
+my ($xd, $svk) = build_test();
+our $output;
+my ($repospath, $path, $repos) = $xd->find_repos ('//', 1);
+
+my $hook = SVN::Hook->new({repospath => $repospath});
+
+$hook->init($_) for SVN::Hook->ALL_HOOKS;
+
+my $tmpdir = tempdir( CLEANUP => 1 );
+
+SVN::Hook->_install_perl_hook($hook->hook_path('_pre-commit/partial'), <<"EOF");
+use SVN::Hook::Redispatch {
+ foo => 'foo_scripts',
+ 'foo/bar' => 'foobar_scripts',
+ bar => 'bar_scripts',
+}, \@ARGV;
+exit 0;
+EOF
+
+SVN::Hook->_install_perl_hook($hook->hook_path('_pre-commit/00worky_log'), <<"EOF");
+open my \$fh, '>>', "$tmpdir/worky";
+print \$fh "this is worky \$ARGV[1]\\n";
+EOF
+
+mkpath [$hook->hook_path('_pre-commit/foo_scripts')];
+SVN::Hook->_install_perl_hook($hook->hook_path('_pre-commit/foo_scripts/die'), <<"EOF");
+die "this is foo die";
+EOF
+
+is_output($svk, 'mkdir', [-m => 'foo', '//foo'],
+ [qr'Committed']);
+
+is_output($svk, 'mkdir', [-m => 'foo', '//foo/shouldtrigger'],
+ [qr'A repository hook failed.*',
+ qr'this is foo die', '']);
+
+is_file_content("$tmpdir/worky", 'this is worky 0-1
+this is worky 1-1
+');
More information about the Bps-public-commit
mailing list