Drop 'fetch', add 'pull', support custom gpg binaries via env.
This commit is contained in:
parent
7164bd6724
commit
03bbbcc350
95
git-sig
95
git-sig
|
@ -6,6 +6,9 @@ readonly MIN_GPG_VERSION=2.2
|
||||||
readonly MIN_OPENSSL_VERSION=1.1
|
readonly MIN_OPENSSL_VERSION=1.1
|
||||||
readonly MIN_GETOPT_VERSION=2.33
|
readonly MIN_GETOPT_VERSION=2.33
|
||||||
|
|
||||||
|
GIT_SIG_GPG_VERIFY_COMMAND=${GIT_SIG_GPG_VERIFY_COMMAND:-gpg}
|
||||||
|
GIT_SIG_SIGN_COMMAND=${GIT_SIG_SIGN_COMMAND:-gpg}
|
||||||
|
|
||||||
## Private Functions
|
## Private Functions
|
||||||
|
|
||||||
### Exit with error message
|
### Exit with error message
|
||||||
|
@ -97,7 +100,7 @@ check_tools(){
|
||||||
for cmd in "$@"; do
|
for cmd in "$@"; do
|
||||||
command -v "$1" >/dev/null || die "Error: $cmd not found"
|
command -v "$1" >/dev/null || die "Error: $cmd not found"
|
||||||
case $cmd in
|
case $cmd in
|
||||||
gpg)
|
${GIT_SIG_VERIFY_COMMAND})
|
||||||
version=$(gpg --version | head -n1 | cut -d" " -f3)
|
version=$(gpg --version | head -n1 | cut -d" " -f3)
|
||||||
check_version "gnupg" "${version}" "${MIN_GPG_VERSION}"
|
check_version "gnupg" "${version}" "${MIN_GPG_VERSION}"
|
||||||
;;
|
;;
|
||||||
|
@ -116,7 +119,7 @@ check_tools(){
|
||||||
### Get primary UID for a given fingerprint
|
### Get primary UID for a given fingerprint
|
||||||
get_uid(){
|
get_uid(){
|
||||||
local -r fp="${1?}"
|
local -r fp="${1?}"
|
||||||
gpg --list-keys --with-colons "${fp}" 2>&1 \
|
${GIT_SIG_VERIFY_COMMAND} --list-keys --with-colons "${fp}" 2>&1 \
|
||||||
| awk -F: '$1 == "uid" {print $10}' \
|
| awk -F: '$1 == "uid" {print $10}' \
|
||||||
| head -n1
|
| head -n1
|
||||||
}
|
}
|
||||||
|
@ -124,7 +127,7 @@ get_uid(){
|
||||||
### Get primary fingerprint for given search
|
### Get primary fingerprint for given search
|
||||||
get_primary_fp(){
|
get_primary_fp(){
|
||||||
local -r search="${1?}"
|
local -r search="${1?}"
|
||||||
gpg --list-keys --with-colons "${search}" 2>&1 \
|
${GIT_SIG_VERIFY_COMMAND} --list-keys --with-colons "${search}" 2>&1 \
|
||||||
| awk -F: '$1 == "fpr" {print $10}' \
|
| awk -F: '$1 == "fpr" {print $10}' \
|
||||||
| head -n1
|
| head -n1
|
||||||
}
|
}
|
||||||
|
@ -132,7 +135,7 @@ get_primary_fp(){
|
||||||
### Get fingerprint for a given pgp file
|
### Get fingerprint for a given pgp file
|
||||||
get_file_fp(){
|
get_file_fp(){
|
||||||
local -r filename="${1?}"
|
local -r filename="${1?}"
|
||||||
gpg --list-packets "${filename}" \
|
${GIT_SIG_VERIFY_COMMAND} --list-packets "${filename}" \
|
||||||
| grep keyid \
|
| grep keyid \
|
||||||
| sed 's/.*keyid //g'
|
| sed 's/.*keyid //g'
|
||||||
}
|
}
|
||||||
|
@ -168,7 +171,7 @@ group_add_fp(){
|
||||||
done
|
done
|
||||||
|
|
||||||
echo "Adding key \"${fp}\" to group \"${group_name}\""
|
echo "Adding key \"${fp}\" to group \"${group_name}\""
|
||||||
gpg --list-keys >/dev/null 2>&1
|
${GIT_SIG_VERIFY_COMMAND} --list-keys >/dev/null 2>&1
|
||||||
printf 'group:0:%s' "${data%?}" \
|
printf 'group:0:%s' "${data%?}" \
|
||||||
| gpgconf --change-options gpg >/dev/null 2>&1
|
| gpgconf --change-options gpg >/dev/null 2>&1
|
||||||
}
|
}
|
||||||
|
@ -176,7 +179,7 @@ group_add_fp(){
|
||||||
### Get fingerprints for a given group
|
### Get fingerprints for a given group
|
||||||
group_get_fps(){
|
group_get_fps(){
|
||||||
local -r group_name=${1?}
|
local -r group_name=${1?}
|
||||||
gpg --with-colons --list-config group \
|
${GIT_SIG_VERIFY_COMMAND} --with-colons --list-config group \
|
||||||
| grep -i "^cfg:group:${group_name}:" \
|
| grep -i "^cfg:group:${group_name}:" \
|
||||||
| cut -d ':' -f4
|
| cut -d ':' -f4
|
||||||
}
|
}
|
||||||
|
@ -221,7 +224,7 @@ sig_generate(){
|
||||||
local -r body="sig:$version:$vcs_ref:$tree_hash:$review_hash:$sig_type"
|
local -r body="sig:$version:$vcs_ref:$tree_hash:$review_hash:$sig_type"
|
||||||
local -r signature=$(\
|
local -r signature=$(\
|
||||||
printf "%s" "$body" \
|
printf "%s" "$body" \
|
||||||
| gpg \
|
| ${GIT_SIG_SIGN_COMMAND} \
|
||||||
--detach-sign \
|
--detach-sign \
|
||||||
--local-user "$key" \
|
--local-user "$key" \
|
||||||
| openssl base64 -A \
|
| openssl base64 -A \
|
||||||
|
@ -286,7 +289,7 @@ verify_git_note(){
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
gpg_sig_raw="$(
|
gpg_sig_raw="$(
|
||||||
gpg --verify --status-fd=1 \
|
${GIT_SIG_VERIFY_COMMAND} --verify --status-fd=1 \
|
||||||
<(printf '%s' "$sig" | openssl base64 -d -A) \
|
<(printf '%s' "$sig" | openssl base64 -d -A) \
|
||||||
<(printf '%s' "$body") 2>/dev/null \
|
<(printf '%s' "$body") 2>/dev/null \
|
||||||
)"
|
)"
|
||||||
|
@ -314,7 +317,13 @@ verify_git_notes(){
|
||||||
verify_git_commit(){
|
verify_git_commit(){
|
||||||
local -r ref="${1:-HEAD}"
|
local -r ref="${1:-HEAD}"
|
||||||
local gpg_sig_raw
|
local gpg_sig_raw
|
||||||
gpg_sig_raw=$(git verify-commit "$ref" --raw 2>&1)
|
gpg_sig_raw=$( \
|
||||||
|
git \
|
||||||
|
-c "gpg.program=$GIT_SIG_VERIFY_COMMAND" \
|
||||||
|
verify-commit "$ref" \
|
||||||
|
--raw \
|
||||||
|
2>&1 \
|
||||||
|
)
|
||||||
parse_gpg_status "$gpg_sig_raw"
|
parse_gpg_status "$gpg_sig_raw"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -468,7 +477,6 @@ cmd_verify() {
|
||||||
--) shift; break ;;
|
--) shift; break ;;
|
||||||
esac done
|
esac done
|
||||||
|
|
||||||
git fetch "$remote" refs/notes/signatures:refs/notes/signatures
|
|
||||||
local -r head=$(git rev-parse --short HEAD)
|
local -r head=$(git rev-parse --short HEAD)
|
||||||
if [ -n "$diff" ] && [ -z "$ref" ]; then
|
if [ -n "$diff" ] && [ -z "$ref" ]; then
|
||||||
while read -r commit; do
|
while read -r commit; do
|
||||||
|
@ -491,49 +499,6 @@ cmd_verify() {
|
||||||
return 1
|
return 1
|
||||||
}
|
}
|
||||||
|
|
||||||
cmd_fetch() {
|
|
||||||
local opts group="" group_fps=""
|
|
||||||
opts="$(getopt -o g: -l group: -n "$PROGRAM" -- "$@")"
|
|
||||||
eval set -- "$opts"
|
|
||||||
while true; do case $1 in
|
|
||||||
-g|--group) group="${2:-1}"; shift 2 ;;
|
|
||||||
--) shift; break ;;
|
|
||||||
esac done
|
|
||||||
[ $# -eq 1 ] || \
|
|
||||||
die "Usage: $PROGRAM fetch <fingerprint> [-g,--group=<group>]"
|
|
||||||
local -r fingerprint=${1}
|
|
||||||
|
|
||||||
if [ -n "$group" ]; then
|
|
||||||
group_fps=$(group_get_fps "${group_name}")
|
|
||||||
if [[ "${group_fps}" == *"${fingerprint}"* ]]; then
|
|
||||||
echo "Key \"${fingerprint}\" is already in group \"${group}\""
|
|
||||||
else
|
|
||||||
group_add_fp "${fingerprint}" "${group}"
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
|
|
||||||
gpg --list-keys "${fingerprint}" > /dev/null 2>&1 \
|
|
||||||
&& echo "Key \"${fingerprint}\" is already in local keychain" \
|
|
||||||
&& return 0
|
|
||||||
|
|
||||||
echo "Requested key is not in keyring. Trying keyservers..."
|
|
||||||
for server in \
|
|
||||||
keys.openpgp.org \
|
|
||||||
ha.pool.sks-keyservers.net \
|
|
||||||
hkp://keyserver.ubuntu.com:80 \
|
|
||||||
hkp://p80.pool.sks-keyservers.net:80 \
|
|
||||||
pgp.mit.edu \
|
|
||||||
; do
|
|
||||||
echo "Fetching key \"${fingerprint}\" from \"${server}\"";
|
|
||||||
gpg \
|
|
||||||
--recv-key \
|
|
||||||
--keyserver "$server" \
|
|
||||||
--keyserver-options timeout=10 \
|
|
||||||
--recv-keys "${fingerprint}" \
|
|
||||||
&& break
|
|
||||||
done
|
|
||||||
}
|
|
||||||
|
|
||||||
cmd_add(){
|
cmd_add(){
|
||||||
local opts method="" push="0"
|
local opts method="" push="0"
|
||||||
opts="$(getopt -o m:p:: -l method:,push:: -n "$PROGRAM" -- "$@")"
|
opts="$(getopt -o m:p:: -l method:,push:: -n "$PROGRAM" -- "$@")"
|
||||||
|
@ -558,17 +523,27 @@ cmd_push() {
|
||||||
-r|--remote) remote="$2"; shift 2 ;;
|
-r|--remote) remote="$2"; shift 2 ;;
|
||||||
--) shift; break ;;
|
--) shift; break ;;
|
||||||
esac done
|
esac done
|
||||||
git fetch "$remote" refs/notes/signatures:refs/notes/signatures
|
|
||||||
git notes --ref signatures merge -s cat_sort_uniq "${remote}"/signatures
|
|
||||||
git push --tags "$remote" refs/notes/signatures
|
git push --tags "$remote" refs/notes/signatures
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cmd_pull() {
|
||||||
|
local opts remote="origin"
|
||||||
|
opts="$(getopt -o r: -l remote: -n "$PROGRAM" -- "$@")"
|
||||||
|
eval set -- "$opts"
|
||||||
|
while true; do case $1 in
|
||||||
|
-r|--remote) remote="$2"; shift 2 ;;
|
||||||
|
--) shift; break ;;
|
||||||
|
esac done
|
||||||
|
git fetch "$remote" refs/notes/signatures:refs/notes/${remote}/signatures
|
||||||
|
git notes --ref signatures merge -s cat_sort_uniq "${remote}"/signatures
|
||||||
|
}
|
||||||
|
|
||||||
cmd_version() {
|
cmd_version() {
|
||||||
cat <<-_EOF
|
cat <<-_EOF
|
||||||
==========================================
|
==========================================
|
||||||
= git-sig: multisig trust for git =
|
= git-sig: multisig trust for git =
|
||||||
= =
|
= =
|
||||||
= v0.3 =
|
= v0.4 =
|
||||||
= =
|
= =
|
||||||
= https://codeberg.org/distrust/git-sig =
|
= https://codeberg.org/distrust/git-sig =
|
||||||
==========================================
|
==========================================
|
||||||
|
@ -587,8 +562,8 @@ cmd_usage() {
|
||||||
Verify m-of-n signatures by given group are present for directory.
|
Verify m-of-n signatures by given group are present for directory.
|
||||||
git sig push [-r,--remote=<remote>]
|
git sig push [-r,--remote=<remote>]
|
||||||
Push all signatures on current ref
|
Push all signatures on current ref
|
||||||
git sig fetch [-g,--group=<group>]
|
git sig pull [-r,--remote=<remote>]
|
||||||
Fetch key by fingerprint. Optionally add to group.
|
Pull all signatures for current ref
|
||||||
git sig help
|
git sig help
|
||||||
Show this text.
|
Show this text.
|
||||||
git sig version
|
git sig version
|
||||||
|
@ -597,7 +572,7 @@ cmd_usage() {
|
||||||
}
|
}
|
||||||
|
|
||||||
# Verify all tools in this list are installed at needed versions
|
# Verify all tools in this list are installed at needed versions
|
||||||
check_tools git head cut find sort sed getopt gpg openssl
|
check_tools git head cut find sort sed getopt openssl ${GIT_SIG_VERIFY_COMMAND}
|
||||||
|
|
||||||
# Allow entire script to be namespaced based on filename
|
# Allow entire script to be namespaced based on filename
|
||||||
readonly PROGRAM="${0##*/}"
|
readonly PROGRAM="${0##*/}"
|
||||||
|
@ -607,8 +582,8 @@ case "$1" in
|
||||||
verify) shift; cmd_verify "$@" ;;
|
verify) shift; cmd_verify "$@" ;;
|
||||||
add) shift; cmd_add "$@" ;;
|
add) shift; cmd_add "$@" ;;
|
||||||
remove) shift; cmd_remove "$@" ;;
|
remove) shift; cmd_remove "$@" ;;
|
||||||
fetch) shift; cmd_fetch "$@" ;;
|
|
||||||
push) shift; cmd_push "$@" ;;
|
push) shift; cmd_push "$@" ;;
|
||||||
|
pull) shift; cmd_pull "$@" ;;
|
||||||
version|--version) shift; cmd_version "$@" ;;
|
version|--version) shift; cmd_version "$@" ;;
|
||||||
help|--help) shift; cmd_usage "$@" ;;
|
help|--help) shift; cmd_usage "$@" ;;
|
||||||
*) cmd_usage "$@" ;;
|
*) cmd_usage "$@" ;;
|
||||||
|
|
Loading…
Reference in New Issue