Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix DNF5 repoquery #522

Merged
merged 1 commit into from
Oct 19, 2024
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
41 changes: 35 additions & 6 deletions qubes-rpc/qvm-template-repo-query
100755 → 100644
Original file line number Diff line number Diff line change
Expand Up @@ -26,11 +26,18 @@ repodir=$(mktemp -d)
trap 'rm -r "$repodir"' EXIT
cat > "$repodir/template.repo"

DNF5=false
if [ "$(readlink /usr/bin/dnf)" = "dnf5" ]; then
DNF5=true
fi

OPTS+=(-y "--setopt=reposdir=${repodir}" --quiet)

# use vendored 'downloadurl' dnf-plugin (fork of 'download' plugin), to print
# all mirrors
OPTS+=("--setopt=pluginpath=/usr/lib/qubes/dnf-plugins")
if ! $DNF5; then
# use vendored 'downloadurl' dnf-plugin (fork of 'download' plugin), to print
# all mirrors
OPTS+=("--setopt=pluginpath=/usr/lib/qubes/dnf-plugins")
fi

if ! command -v dnf >/dev/null; then
echo "ERROR: dnf command is missing, please use newer template for your UpdateVM to download templates." >&2
Expand All @@ -49,16 +56,38 @@ touch -r "$hashfile" "$repodir/template.repo"
RET=0

if [ "$1" = "query" ]; then
dnf repoquery "${OPTS[@]}" --qf='%{name}|%{epoch}|%{version}|%{release}|%{reponame}|%{downloadsize}|%{buildtime}|%{license}|%{url}|%{summary}|%{description}|' "$SPEC"
if $DNF5; then
dnf repoquery "${OPTS[@]}" --qf='%{name}|%{epoch}|%{version}|%{release}|%{repoid}|%{downloadsize}|%{buildtime}|%{license}|%{url}|%{summary}|%{description}|\n' "$SPEC"
else
dnf repoquery "${OPTS[@]}" --qf='%{name}|%{epoch}|%{version}|%{release}|%{repoid}|%{downloadsize}|%{buildtime}|%{license}|%{url}|%{summary}|%{description}|' "$SPEC"
fi
RET="$?"
elif [ "$1" = "download" ]; then
# Download/retry algorithm: take mirrors in random order. In this order,
# try to download from the first one - if download failed but anything was
# downloaded - retry from the same one. If download failed and nothing was
# downloaded, go to the next one. The intention is to retry on interrupted
# connection, but skip mirrors that are not synchronized yet.
urls="$(dnf downloadurl "${OPTS[@]}" --url --all-mirrors "$SPEC" | shuf)"
readarray -t urls <<<"$urls"
declare -a urls=()
alimirjamali marked this conversation as resolved.
Show resolved Hide resolved
if $DNF5 && dnf download --help | grep -q allmirrors; then
# The smartest case. DNF5 on Fedora 41 with --allmirrors patch
space_separated_urls="$(dnf download "${OPTS[@]}" --url --allmirrors "$SPEC")"
readarray -d ' ' -t urls <<<"$space_separated_urls"
urls=( $(shuf -e "${urls[@]}") )
elif $DNF5; then
# The middle case. DNF5 on Fedora 41 before --allmirror patch
# TODO: Phase out after DNF5 --allmirrors patch is released
url="$(dnf download "${OPTS[@]}" --url "$SPEC")"
urls=("$url")
else
# The old DNF4 on Fedora 40 and other old templates
# use vendored 'downloadurl' dnf-plugin (fork of 'download' plugin),
# to print all mirrors.
# TODO: Phase out after DNF4 is EOL
OPTS+=("--setopt=pluginpath=/usr/lib/qubes/dnf-plugins")
urls="$(dnf downloadurl "${OPTS[@]}" --url --all-mirrors "$SPEC" | shuf)"
readarray -t urls <<<"$urls"
fi
downloaded=0
status_file="$repodir/download-status.tmp"
for url in "${urls[@]}"; do
Expand Down