在典型的安裝中,會新增多個 apt GPG 金鑰,無論是用於 PPA 還是其他來源,但隨後會不再使用。
在 GUI(軟體屬性)中很難識別哪些金鑰實際用於哪些儲存庫。
有沒有一種簡單的方法來識別哪些鍵已被使用,以便可以刪除所有其他鍵?
在我看來,這有一些安全隱憂。如果儲存庫擁有者遺失了他們的私鑰並更新儲存庫以使用新金鑰,那麼許多人仍然安裝了舊的(不可信的)金鑰,對吧?
答案1
刪除未使用的密鑰非常簡單,但就像添加密鑰一樣,您是負責做作業並決定哪些密鑰不再使用並且可以刪除的人。
首先列出您目前擁有的 apt 金鑰sudo apt-key list
。
一旦您確定不再需要某個金鑰,您只需使用 即可將其刪除sudo apt-key del KEYID
。
使用 list 命令,您通常可以查看每個金鑰的含義,特別是如果它來自 ppa,因為它通常有一個包含“Launchpad PPA for John”之類的 uid。因此,如果您從來源中刪除了該 ppa 並且不再使用它,則可以安全地刪除它們。
有時您可能需要快速谷歌來了解特定密鑰的來源,例如,單聲道密鑰具有 uid“Xamarin Public Jenkins”,如果您谷歌 xamarin,您可以看到該密鑰的來源。另外,如果您不確定,您可以隨時返回 bash 歷史記錄並找到您新增的金鑰。
man apt-key
是否有更多資訊和其他命令。
答案2
我編寫了一個腳本,可以自動識別(並可選擇刪除)未使用的 GPG 金鑰。
#!/bin/bash
#------------------------------------
# Script that identifies and optionally removes unused trusted gpg keys.
# These keys are usually added to install software from non-standard repositories (e.g. PPAs)
# TODO:
# - what if source repo is not reachable
# - dunno why but the delete doesn't actually delete keys anymore ¯\_(ツ)_/¯
# - dunno why but slack key gets detected as unused even if slack is on the system ¯\_(ツ)_/¯
#------------------------------------
usage() {
echo "Usage: $(basename "$0") [-b] [-d] [-h]" 1>&2
echo "prints to stdout the unused keys in the format <keyid> <userid>" 1>&2
echo "-b, backups trusted.gpg and trusted.gpg.d/ appending .bak (requires superuser)" 1>&2
echo "-d, deletes unused keys (requires superuser)" 1>&2
echo "-h, shows this help" 1>&2
}
backup=0
delete=0
while getopts ":bdh" o; do
case "${o}" in
b)
backup=1
;;
d)
delete=1
;;
h)
usage
exit 0
;;
*)
usage
exit 1
;;
esac
done
shift $((OPTIND-1))
# create directory in /tmp with random name
tmpdir=$(mktemp -d)
#echo "storing tmp files in $tmpdir" 1>&2
# get list of sources
grep -h ^deb /etc/apt/sources.list /etc/apt/sources.list.d/*.list > "${tmpdir}"/sources
# get list of releases files
# first sed expression removes content between square brackets (such as architecture specifications)
# awk is used to get only the source url and the distro we are using
# the 2 subsequent sed expressions are used piece everything together and generate the url to the Release.gpg file we need
# sort and uniq are used to eliminate duplicate entries
sed -e "s/\[.*\] //" "${tmpdir}/sources" | awk '{print $2" "$3}' | sed -E -e "s/\/? /\/dists\//" | sed -e "s/$/\/Release.gpg/" | sort | uniq > "${tmpdir}"/releases
# for each source, compute the keyid and save it in a file
while read -r url; do
domain=$(echo $url | awk -F/ '{print $3}')
#echo "processing ${url}"
wget -q -T 10 -O "${tmpdir}"/"${domain}"_Release.gpg "$url"
gpg --list-packets "${tmpdir}"/"${domain}"_Release.gpg | grep "keyid" | grep -Eo "[0-9A-F]{16}" >> "${tmpdir}"/sourcekeyidstemp
done <"${tmpdir}"/releases
# remove duplicate entries
sort "${tmpdir}"/sourcekeyidstemp | uniq > "${tmpdir}"/sourcekeyids
# for each trusted gpg key, extract his keyid and userid
gpg --list-packets /etc/apt/trusted.gpg | grep -A 8 "public key packet" | grep -E "keyid:|user ID" | grep -oE "[0-9A-F]{16}|\".*\"" | awk '{(getline tmp); print $0,tmp}' > "${tmpdir}"/trustedkeys
for f in /etc/apt/trusted.gpg.d/*.gpg; do
gpg --list-packets "$f" | grep -A 8 "public key packet" | grep -E "keyid:|user ID" | grep -oE "[0-9A-F]{16}|\".*\"" | awk '{(getline tmp); print $0,tmp}' >> "${tmpdir}"/trustedkeys
done
# for each trusted gpg key, check if in use
touch "${tmpdir}"/unusedkeys
while read -r line; do
keyid=$(echo "$line" | cut -d "\"" -f 1)
userid=$(echo "$line" | cut -d "\"" -f 2)
check=$(grep ${keyid} "${tmpdir}"/sourcekeyids)
if [ -z "$check" ]; then
echo "${keyid} ${userid}" >> "${tmpdir}"/unusedkeys
fi
done <"${tmpdir}"/trustedkeys
# backup gpg keys
if [ $backup -eq 1 ]; then
sudo cp /etc/apt/trusted.gpg /etc/apt/trusted.gpg.bak
sudo cp -r /etc/apt/trusted.gpg.d/ /etc/apt/trusted.gpg.d.bak
fi
# delete unused gpg keys
if [ $delete -eq 1 ]; then
while read -r line; do
keyid=$(echo "$line" | cut -d "\"" -f 1)
sudo apt-key del "$keyid" >/dev/null
done <"${tmpdir}"/unusedkeys
echo "deleted keys:"
fi
# print unused keys
cat "${tmpdir}"/unusedkeys
它相當笨重,但很有效。可能有錯誤,使用風險自擔。
該腳本的工作流程如下:
- 透過從線上儲存庫取得 Release.gpg 檔案來提取所有 apt 來源的 KEYID
- 提取所有本地可信任密鑰的 KEYID。
- 檢查某些 KEYID 是否存在於本地,並且不存在於從線上來源提取的 KEYID 中。這些是未使用的鍵。
編輯:固定鏈接編輯:將程式碼貼到此處,因為我厭倦了修復鏈接