diff options
Diffstat (limited to 't/t5534-push-signed.sh')
-rwxr-xr-x | t/t5534-push-signed.sh | 154 |
1 files changed, 135 insertions, 19 deletions
diff --git a/t/t5534-push-signed.sh b/t/t5534-push-signed.sh index 030331f..c91a62b 100755 --- a/t/t5534-push-signed.sh +++ b/t/t5534-push-signed.sh @@ -2,6 +2,9 @@ test_description='signed push' +GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME=main +export GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME + . ./test-lib.sh . "$TEST_DIRECTORY"/lib-gpg.sh @@ -9,11 +12,11 @@ prepare_dst () { rm -fr dst && test_create_repo dst && - git push dst master:noop master:ff master:noff + git push dst main:noop main:ff main:noff } test_expect_success setup ' - # master, ff and noff branches pointing at the same commit + # main, ff and noff branches pointing at the same commit test_tick && git commit --allow-empty -m initial && @@ -32,8 +35,7 @@ test_expect_success setup ' test_expect_success 'unsigned push does not send push certificate' ' prepare_dst && - mkdir -p dst/.git/hooks && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -49,8 +51,7 @@ test_expect_success 'unsigned push does not send push certificate' ' test_expect_success 'talking with a receiver without push certificate support' ' prepare_dst && - mkdir -p dst/.git/hooks && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -66,22 +67,19 @@ test_expect_success 'talking with a receiver without push certificate support' ' test_expect_success 'push --signed fails with a receiver without push certificate support' ' prepare_dst && - mkdir -p dst/.git/hooks && test_must_fail git push --signed dst noop ff +noff 2>err && - test_i18ngrep "the receiving end does not support" err + test_grep "the receiving end does not support" err ' test_expect_success 'push --signed=1 is accepted' ' prepare_dst && - mkdir -p dst/.git/hooks && test_must_fail git push --signed=1 dst noop ff +noff 2>err && - test_i18ngrep "the receiving end does not support" err + test_grep "the receiving end does not support" err ' test_expect_success GPG 'no certificate for a signed push with no update' ' prepare_dst && - mkdir -p dst/.git/hooks && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && if test -n "${GIT_PUSH_CERT-}" then git cat-file blob $GIT_PUSH_CERT >../push-cert @@ -93,9 +91,8 @@ test_expect_success GPG 'no certificate for a signed push with no update' ' test_expect_success GPG 'signed push sends push certificate' ' prepare_dst && - mkdir -p dst/.git/hooks && git -C dst config receive.certnonceseed sekrit && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -134,6 +131,52 @@ test_expect_success GPG 'signed push sends push certificate' ' test_cmp expect dst/push-cert-status ' +test_expect_success GPGSSH 'ssh signed push sends push certificate' ' + prepare_dst && + git -C dst config gpg.ssh.allowedSignersFile "${GPGSSH_ALLOWED_SIGNERS}" && + git -C dst config receive.certnonceseed sekrit && + test_hook -C dst post-receive <<-\EOF && + # discard the update list + cat >/dev/null + # record the push certificate + if test -n "${GIT_PUSH_CERT-}" + then + git cat-file blob $GIT_PUSH_CERT >../push-cert + fi && + + cat >../push-cert-status <<E_O_F + SIGNER=${GIT_PUSH_CERT_SIGNER-nobody} + KEY=${GIT_PUSH_CERT_KEY-nokey} + STATUS=${GIT_PUSH_CERT_STATUS-nostatus} + NONCE_STATUS=${GIT_PUSH_CERT_NONCE_STATUS-nononcestatus} + NONCE=${GIT_PUSH_CERT_NONCE-nononce} + E_O_F + + EOF + + test_config gpg.format ssh && + test_config user.signingkey "${GPGSSH_KEY_PRIMARY}" && + FINGERPRINT=$(ssh-keygen -lf "${GPGSSH_KEY_PRIMARY}" | awk "{print \$2;}") && + git push --signed dst noop ff +noff && + + ( + cat <<-\EOF && + SIGNER=principal with number 1 + KEY=FINGERPRINT + STATUS=G + NONCE_STATUS=OK + EOF + sed -n -e "s/^nonce /NONCE=/p" -e "/^$/q" dst/push-cert + ) | sed -e "s|FINGERPRINT|$FINGERPRINT|" >expect && + + noop=$(git rev-parse noop) && + ff=$(git rev-parse ff) && + noff=$(git rev-parse noff) && + grep "$noop $ff refs/heads/ff" dst/push-cert && + grep "$noop $noff refs/heads/noff" dst/push-cert && + test_cmp expect dst/push-cert-status +' + test_expect_success GPG 'inconsistent push options in signed push not allowed' ' # First, invoke receive-pack with dummy input to obtain its preamble. prepare_dst && @@ -173,9 +216,8 @@ test_expect_success GPG 'inconsistent push options in signed push not allowed' ' test_expect_success GPG 'fail without key and heed user.signingkey' ' prepare_dst && - mkdir -p dst/.git/hooks && git -C dst config receive.certnonceseed sekrit && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -223,9 +265,8 @@ test_expect_success GPG 'fail without key and heed user.signingkey' ' test_expect_success GPGSM 'fail without key and heed user.signingkey x509' ' test_config gpg.format x509 && prepare_dst && - mkdir -p dst/.git/hooks && git -C dst config receive.certnonceseed sekrit && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -262,7 +303,7 @@ test_expect_success GPGSM 'fail without key and heed user.signingkey x509' ' EOF sed -n -e "s/^nonce /NONCE=/p" -e "/^$/q" dst/push-cert ) >expect.in && - key=$(cat "${GNUPGHOME}/trustlist.txt" | cut -d" " -f1 | tr -d ":") && + key=$(cut -d" " -f1 <"${GNUPGHOME}/trustlist.txt" | tr -d ":") && sed -e "s/^KEY=/KEY=${key}/" expect.in >expect && noop=$(git rev-parse noop) && @@ -273,4 +314,79 @@ test_expect_success GPGSM 'fail without key and heed user.signingkey x509' ' test_cmp expect dst/push-cert-status ' +test_expect_success GPGSSH 'fail without key and heed user.signingkey ssh' ' + test_config gpg.format ssh && + prepare_dst && + git -C dst config gpg.ssh.allowedSignersFile "${GPGSSH_ALLOWED_SIGNERS}" && + git -C dst config receive.certnonceseed sekrit && + test_hook -C dst post-receive <<-\EOF && + # discard the update list + cat >/dev/null + # record the push certificate + if test -n "${GIT_PUSH_CERT-}" + then + git cat-file blob $GIT_PUSH_CERT >../push-cert + fi && + + cat >../push-cert-status <<E_O_F + SIGNER=${GIT_PUSH_CERT_SIGNER-nobody} + KEY=${GIT_PUSH_CERT_KEY-nokey} + STATUS=${GIT_PUSH_CERT_STATUS-nostatus} + NONCE_STATUS=${GIT_PUSH_CERT_NONCE_STATUS-nononcestatus} + NONCE=${GIT_PUSH_CERT_NONCE-nononce} + E_O_F + + EOF + + test_config user.email hasnokey@nowhere.com && + test_config gpg.format ssh && + test_config user.signingkey "" && + ( + sane_unset GIT_COMMITTER_EMAIL && + test_must_fail git push --signed dst noop ff +noff + ) && + test_config user.signingkey "${GPGSSH_KEY_PRIMARY}" && + FINGERPRINT=$(ssh-keygen -lf "${GPGSSH_KEY_PRIMARY}" | awk "{print \$2;}") && + git push --signed dst noop ff +noff && + + ( + cat <<-\EOF && + SIGNER=principal with number 1 + KEY=FINGERPRINT + STATUS=G + NONCE_STATUS=OK + EOF + sed -n -e "s/^nonce /NONCE=/p" -e "/^$/q" dst/push-cert + ) | sed -e "s|FINGERPRINT|$FINGERPRINT|" >expect && + + noop=$(git rev-parse noop) && + ff=$(git rev-parse ff) && + noff=$(git rev-parse noff) && + grep "$noop $ff refs/heads/ff" dst/push-cert && + grep "$noop $noff refs/heads/noff" dst/push-cert && + test_cmp expect dst/push-cert-status +' + +test_expect_success GPG 'failed atomic push does not execute GPG' ' + prepare_dst && + git -C dst config receive.certnonceseed sekrit && + write_script gpg <<-EOF && + # should check atomic push locally before running GPG. + exit 1 + EOF + test_must_fail env PATH="$TRASH_DIRECTORY:$PATH" git push \ + --signed --atomic --porcelain \ + dst noop ff noff >out 2>err && + + test_grep ! "gpg failed to sign" err && + cat >expect <<-EOF && + To dst + = refs/heads/noop:refs/heads/noop [up to date] + ! refs/heads/ff:refs/heads/ff [rejected] (atomic push failed) + ! refs/heads/noff:refs/heads/noff [rejected] (non-fast-forward) + Done + EOF + test_cmp expect out +' + test_done |