diff --git a/src/Gitolite/Conf/Load.pm b/src/Gitolite/Conf/Load.pm index f1d342c..42a4294 100644 --- a/src/Gitolite/Conf/Load.pm +++ b/src/Gitolite/Conf/Load.pm @@ -63,6 +63,7 @@ my $last_repo = ''; sub access { my ( $repo, $user, $aa, $ref ) = @_; + my $deny_rules = option($repo, 'deny-rules'); load($repo); # when a real repo doesn't exist, ^C is a pre-requisite for any other @@ -81,7 +82,7 @@ sub access { trace( 3, "perm=$perm, refex=$refex" ); # skip 'deny' rules if the ref is not (yet) known - next if $perm eq '-' and $ref eq 'any'; + next if $perm eq '-' and $ref eq 'any' and not $deny_rules; # rule matches if ref matches or ref is any (see gitolite-shell) next unless $ref =~ /^$refex/ or $ref eq 'any'; diff --git a/t/deny-rules-2.t b/t/deny-rules-2.t new file mode 100755 index 0000000..d59f144 --- /dev/null +++ b/t/deny-rules-2.t @@ -0,0 +1,172 @@ +#!/usr/bin/perl +use strict; +use warnings; + +# this is hardcoded; change it if needed +use lib "src"; +use Gitolite::Test; + +# more on deny-rules +# ---------------------------------------------------------------------- + +try "plan 126"; + +try " + DEF GOOD = /refs/\\.\\*/ + DEF BAD = /DENIED/ + + DEF Ryes = gitolite access %1 %2 R any; ok; GOOD + DEF Rno = gitolite access %1 %2 R any; !ok; BAD + + DEF Wyes = gitolite access %1 %2 W any; ok; GOOD + DEF Wno = gitolite access %1 %2 W any; !ok; BAD + + DEF GWyes = Ryes %1 gitweb + DEF GWno = Rno %1 gitweb + + DEF GDyes = Ryes %1 daemon + DEF GDno = Rno %1 daemon +"; + +confreset;confadd ' + repo one + RW+ = u1 + R = u2 + - = u2 u3 + R = @all +'; + +try "ADMIN_PUSH set1; !/FATAL/" or die text(); + +try " + Wyes one u1 + + Ryes one u2 + Wno one u2 + + Ryes one u3 + Wno one u3 + + Ryes one u6 + Wno one u6 + + GDyes one + GWyes one +"; + +confadd ' + option deny-rules = 1 +'; + +try "ADMIN_PUSH set1; !/FATAL/" or die text(); + +try " + Wyes one u1 + + Ryes one u2 + Wno one u2 + + Rno one u3 + + Ryes one u6 + Wno one u6 + + GDyes one + GWyes one +"; + +confadd ' + repo two + RW+ = u1 + R = u2 + - = u2 u3 gitweb daemon + R = @all +'; + +try "ADMIN_PUSH set1; !/FATAL/" or die text(); + +try " + GWyes two + GDyes two +"; + +confadd ' + option deny-rules = 1 +'; + +try "ADMIN_PUSH set1; !/FATAL/" or die text(); + +try " + GWno two + GDno two +"; + +# set 3 -- allow gitweb to all but admin repo + +confadd ' + repo gitolite-admin + - = gitweb daemon + option deny-rules = 1 + + repo three + RW+ = u3 + R = gitweb daemon +'; + +try "ADMIN_PUSH set1; !/FATAL/" or die text(); + +try " + GDyes three + GWyes three + GDno gitolite-admin + GWno gitolite-admin +"; + +# set 4 -- allow gitweb to all but admin repo + +confadd ' + repo four + RW+ = u4 + - = gitweb daemon + + repo @all + R = @all +'; +try "ADMIN_PUSH set1; !/FATAL/" or die text(); + +try " + GDyes four + GWyes four + GDno gitolite-admin + GWno gitolite-admin +"; + +# set 5 -- go wild + +confreset; confadd ' + repo foo/..* + C = u1 + RW+ = CREATOR + - = gitweb daemon + R = @all + + repo bar/..* + C = u2 + RW+ = CREATOR + - = gitweb daemon + R = @all + option deny-rules = 1 +'; +try "ADMIN_PUSH set1; !/FATAL/" or die text(); + +try " + glt ls-remote u1 file:///foo/one + glt ls-remote u2 file:///bar/two + Wyes foo/one u1 + Wyes bar/two u2 + + GDyes foo/one + GDyes foo/one + GWno bar/two + GWno bar/two +"; diff --git a/t/deny-rules.t b/t/deny-rules.t new file mode 100755 index 0000000..2492887 --- /dev/null +++ b/t/deny-rules.t @@ -0,0 +1,67 @@ +#!/usr/bin/perl +use strict; +use warnings; + +# this is hardcoded; change it if needed +use lib "src"; +use Gitolite::Test; + +# branch permissions test +# ---------------------------------------------------------------------- + +try "plan 11"; + +confreset;confadd ' + # start with... + + repo gitolite-admin + - = gitweb daemon + option deny-rules = 1 + + # main ruleset goes here + + @ga = a + @gb = b + @gc = c + + # and end with + + repo @ga + RW = u1 + - = @all + option deny-rules = 1 + + repo @gb + RW = u2 + - = daemon + option deny-rules = 1 + + repo @gc + RW = u3 + + repo @all + R = @all + +'; + +try "ADMIN_PUSH set1; !/FATAL/" or die text(); + +my $rb = `gitolite query-rc -n GL_REPO_BASE`; +try " + cat $ENV{HOME}/projects.list; ok +"; +cmp 'b.git +c.git +testing.git +'; + +try " + cd .. + cd .. + echo $rb + find $rb -name git-daemon-export-ok | sort + perl s,$rb/,,g +"; +cmp 'c.git/git-daemon-export-ok +testing.git/git-daemon-export-ok +'