t5563: add tests for basic and anoymous HTTP access
Add a test showing simple anoymous HTTP access to an unprotected repository, that results in no credential helper invocations. Also add a test demonstrating simple basic authentication with simple credential helper support. Leverage a no-parsed headers (NPH) CGI script so that we can directly control the HTTP responses to simulate a multitude of good, bad and ugly remote server implementations around auth. Signed-off-by: Matthew John Cheetham <mjcheetham@outlook.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
Matthew John Cheetham committed
Feb 27, 2023 at 17:20 UTC
988aad99b44f3fb3f04f4a75cadf0dbb7ac89ffe
4 files changed
+129
t/lib-httpd.sh
+1
@@ -137,6 +137,7 @@ prepare_httpd() {
137
install_script error-smart-http.sh
138
install_script error.sh
139
install_script apply-one-time-perl.sh
140
+ install_script nph-custom-auth.sh
141
142
ln -s "$LIB_HTTPD_MODULE_PATH" "$HTTPD_ROOT_PATH/modules"
143
t/lib-httpd/apache.conf
+6
@@ -135,6 +135,11 @@ Alias /auth/dumb/ www/auth/dumb/
135
SetEnv GIT_HTTP_EXPORT_ALL
136
SetEnv GIT_PROTOCOL
137
</LocationMatch>
138
+<LocationMatch /custom_auth/>
139
+ SetEnv GIT_EXEC_PATH ${GIT_EXEC_PATH}
140
+ SetEnv GIT_HTTP_EXPORT_ALL
141
+ CGIPassAuth on
142
+</LocationMatch>
143
ScriptAlias /smart/incomplete_length/git-upload-pack incomplete-length-upload-pack-v2-http.sh/
144
ScriptAlias /smart/incomplete_body/git-upload-pack incomplete-body-upload-pack-v2-http.sh/
145
ScriptAlias /smart/no_report/git-receive-pack error-no-report.sh/
@@ -144,6 +149,7 @@ ScriptAlias /broken_smart/ broken-smart-http.sh/
149
ScriptAlias /error_smart/ error-smart-http.sh/
150
ScriptAlias /error/ error.sh/
151
ScriptAliasMatch /one_time_perl/(.*) apply-one-time-perl.sh/$1
152
+ScriptAliasMatch /custom_auth/(.*) nph-custom-auth.sh/$1
153
<Directory ${GIT_EXEC_PATH}>
154
Options FollowSymlinks
155
</Directory>
t/lib-httpd/nph-custom-auth.sh
new
+39
@@ -0,0 +1,39 @@
1
+#!/bin/sh
2
+
3
+VALID_CREDS_FILE=custom-auth.valid
4
+CHALLENGE_FILE=custom-auth.challenge
5
+
6
+#
7
+# If $VALID_CREDS_FILE exists in $HTTPD_ROOT_PATH, consider each line as a valid
8
+# credential for the current request. Each line in the file is considered a
9
+# valid HTTP Authorization header value. For example:
10
+#
11
+# Basic YWxpY2U6c2VjcmV0LXBhc3N3ZA==
12
+#
13
+# If $CHALLENGE_FILE exists in $HTTPD_ROOT_PATH, output the contents as headers
14
+# in a 401 response if no valid authentication credentials were included in the
15
+# request. For example:
16
+#
17
+# WWW-Authenticate: Bearer authorize_uri="id.example.com" p=1 q=0
18
+# WWW-Authenticate: Basic realm="example.com"
19
+#
20
+
21
+if test -n "$HTTP_AUTHORIZATION" && \
22
+ grep -Fqsx "${HTTP_AUTHORIZATION}" "$VALID_CREDS_FILE"
23
+then
24
+ # Note that although git-http-backend returns a status line, it
25
+ # does so using a CGI 'Status' header. Because this script is an
26
+ # No Parsed Headers (NPH) script, we must return a real HTTP
27
+ # status line.
28
+ # This is only a test script, so we don't bother to check for
29
+ # the actual status from git-http-backend and always return 200.
30
+ echo 'HTTP/1.1 200 OK'
31
+ exec "$GIT_EXEC_PATH"/git-http-backend
32
+fi
33
+
34
+echo 'HTTP/1.1 401 Authorization Required'
35
+if test -f "$CHALLENGE_FILE"
36
+then
37
+ cat "$CHALLENGE_FILE"
38
+fi
39
+echo
t/t5563-simple-http-auth.sh
new
+83
@@ -0,0 +1,83 @@
1
+#!/bin/sh
2
+
3
+test_description='test http auth header and credential helper interop'
4
+
5
+. ./test-lib.sh
6
+. "$TEST_DIRECTORY"/lib-httpd.sh
7
+
8
+start_httpd
9
+
10
+test_expect_success 'setup_credential_helper' '
11
+ mkdir "$TRASH_DIRECTORY/bin" &&
12
+ PATH=$PATH:"$TRASH_DIRECTORY/bin" &&
13
+ export PATH &&
14
+
15
+ CREDENTIAL_HELPER="$TRASH_DIRECTORY/bin/git-credential-test-helper" &&
16
+ write_script "$CREDENTIAL_HELPER" <<-\EOF
17
+ cmd=$1
18
+ teefile=$cmd-query.cred
19
+ catfile=$cmd-reply.cred
20
+ sed -n -e "/^$/q" -e "p" >>$teefile
21
+ if test "$cmd" = "get"
22
+ then
23
+ cat $catfile
24
+ fi
25
+ EOF
26
+'
27
+
28
+set_credential_reply () {
29
+ cat >"$TRASH_DIRECTORY/$1-reply.cred"
30
+}
31
+
32
+expect_credential_query () {
33
+ cat >"$TRASH_DIRECTORY/$1-expect.cred" &&
34
+ test_cmp "$TRASH_DIRECTORY/$1-expect.cred" \
35
+ "$TRASH_DIRECTORY/$1-query.cred"
36
+}
37
+
38
+per_test_cleanup () {
39
+ rm -f *.cred &&
40
+ rm -f "$HTTPD_ROOT_PATH"/custom-auth.valid \
41
+ "$HTTPD_ROOT_PATH"/custom-auth.challenge
42
+}
43
+
44
+test_expect_success 'setup repository' '
45
+ test_commit foo &&
46
+ git init --bare "$HTTPD_DOCUMENT_ROOT_PATH/repo.git" &&
47
+ git push --mirror "$HTTPD_DOCUMENT_ROOT_PATH/repo.git"
48
+'
49
+
50
+test_expect_success 'access using basic auth' '
51
+ test_when_finished "per_test_cleanup" &&
52
+
53
+ set_credential_reply get <<-EOF &&
54
+ username=alice
55
+ password=secret-passwd
56
+ EOF
57
+
58
+ # Basic base64(alice:secret-passwd)
59
+ cat >"$HTTPD_ROOT_PATH/custom-auth.valid" <<-EOF &&
60
+ Basic YWxpY2U6c2VjcmV0LXBhc3N3ZA==
61
+ EOF
62
+
63
+ cat >"$HTTPD_ROOT_PATH/custom-auth.challenge" <<-EOF &&
64
+ WWW-Authenticate: Basic realm="example.com"
65
+ EOF
66
+
67
+ test_config_global credential.helper test-helper &&
68
+ git ls-remote "$HTTPD_URL/custom_auth/repo.git" &&
69
+
70
+ expect_credential_query get <<-EOF &&
71
+ protocol=http
72
+ host=$HTTPD_DEST
73
+ EOF
74
+
75
+ expect_credential_query store <<-EOF
76
+ protocol=http
77
+ host=$HTTPD_DEST
78
+ username=alice
79
+ password=secret-passwd
80
+ EOF
81
+'
82
+
83
+test_done