#!/bin/sh
# report about status of build master
. "${0%/*}/../conf/default.conf"
usage() {
>&2 echo ''
>&2 echo 'build-master-status: report about status of build master'
>&2 echo ''
>&2 echo 'possible options:'
>&2 echo ' -w|--web:'
>&2 echo ' Output to webserver instead of stdout.'
>&2 echo ' -h|--help:'
>&2 echo ' Show this help and exit.'
[ -z "$1" ] && exit 1 || exit $1
}
eval set -- "$(
getopt -o hw \
--long help \
--long web \
-n "$(basename "$0")" -- "$@" || \
echo usage
)"
web=false
while true
do
case "$1" in
-h|--help)
usage 0
;;
-w|--web)
web=true
;;
--)
shift
break
;;
*)
>&2 echo 'Whoops, forgot to implement option "'"$1"'" internally.'
exit 42
;;
esac
shift
done
if [ $# -ne 0 ]; then
>&2 echo 'Too many arguments.'
usage
fi
tmp_dir=$(mktemp -d)
trap 'rm -rf --one-file-system "${tmp_dir}"' EXIT
stable=$(
ls_master_mirror 'i686' | \
grep -v 'testing$\|staging$\|-unstable$' | \
while read -r dir; do
ls_master_mirror "i686/${dir}"
done | \
grep -c '\.pkg\.tar\.xz$'
)
tasks=$(
grep -c '^\S\+ \S\+ \S\+ \S\+$' \
"${work_dir}/build-list"
) || true
pending_packages=$(
grep '^\S\+ \S\+ \S\+ \S\+$' "${work_dir}/build-list" | \
tr ' ' '.' | \
while read -r package; do
generate_package_metadata "${package}" 2>&1 > /dev/null
cat "${work_dir}/package-infos/${package}.packages"
done |
wc -l
)
next_tasks=$(
(
grep -vxF 'break_loops' "${work_dir}/build-list"
ls "${work_dir}/package-states" | \
grep '\.broken$' | \
sed '
s|\.\([^.]\+\)\.\([^.]\+\)\.\([^.]\+\)\.[^.]\+$| \1 \2 \3|
p
'
) | \
sort | \
uniq -u | \
while read -r package git_revision mod_git_revision repository; do
if [ -z "$(find_dependencies_on_build_list "${package}" "${git_revision}" "${mod_git_revision}" "${repository}")" ]; then
echo "${package}" "${git_revision}" "${mod_git_revision}" "${repository}"
fi
done | \
wc -l
)
staging=$(
ls_master_mirror 'i686' | \
grep 'staging$' | \
while read -r dir; do
ls_master_mirror "i686/${dir}"
done | \
grep -c '\.pkg\.tar\.xz$'
)
testing=$(
ls_master_mirror 'i686' | \
grep 'testing$' | \
while read -r dir; do
ls_master_mirror "i686/${dir}"
done | \
grep -c '\.pkg\.tar\.xz$'
)
(
ls "${work_dir}/package-states/" | \
grep '\.broken$' | \
sed 's|\.\([^.]\+\)\.\([^.]\+\)\.\([^.]\+\)\.[^.]\+$| \1 \2 \3|' | \
while read -r pkg rev mod_rev repo; do
if [ -z "$(find_dependencies_on_build_list "${pkg}" "${rev}" "${mod_rev}" "${repo}")" ]; then
echo "${pkg}"
fi
done
(
ls "${work_dir}/build-list.loops" | \
grep '^loop_[0-9]\+$' | \
sed "s|^|${work_dir}/build-list.loops/|" | \
xargs -r cat | \
sort -u
ls "${work_dir}/package-states/" | \
grep '\.broken$' | \
sed 's|\(\.[^.]\+\)\{4\}||' | \
sort -u
) | \
sort | \
uniq -d
) | \
sort -u > \
"${tmp_dir}/broken-packages-names"
broken=$(
wc -l < \
"${tmp_dir}/broken-packages-names"
)
blocked=$(
ls "${work_dir}/package-states/" | \
grep -c '\.blocked$'
) || true
locked=$(
ls "${work_dir}/package-states/" | \
grep -c '\.locked$'
) || true
loops=$(
ls "${work_dir}/build-list.loops" | \
grep -c '^loop_[0-9]\+$'
) || true
looped_packages=$(
ls "${work_dir}/build-list.loops" | \
grep '^loop_[0-9]\+$' | \
sed "s|^|${work_dir}/build-list.loops/|" | \
xargs -r cat | \
sort -u | \
wc -l
)
printf 'The mirror master contains %d stable packages (vs. ca. %d planned).\n' \
"${stable}" \
"$((${staging}+${testing}+${pending_packages}))" >> \
"${tmp_dir}/build-master-status.html"
printf 'The build list contains %d tasks (incl. broken: %d, leading to %d packages), of which %s can be built immediately.\n' \
"$((${tasks}-${broken}))" \
"${tasks}" \
"${pending_packages}" \
"${next_tasks}" >> \
"${tmp_dir}/build-master-status.html"
printf 'There are %d testing and %d staging packages.\n' \
"${testing}" \
"${staging}" >> \
"${tmp_dir}/build-master-status.html"
printf 'There are %d broken package builds.\n' \
"${broken}" >> \
"${tmp_dir}/build-master-status.html"
if [ "${loops}" -ne 0 ]; then
printf 'There are %d loops containing %d package builds.\n' \
"${loops}" \
"${looped_packages}" >> \
"${tmp_dir}/build-master-status.html"
fi
if [ $((${broken}+${testing}+${staging})) -ne 0 ]; then
printf '%.1f%% of all packages are broken.\n' \
"$(
echo "scale=10; 100*${broken}/(${broken}+${testing}+${staging})" | \
bc
)" >> \
"${tmp_dir}/build-master-status.html"
fi
if [ $((${testing}+${staging}+${pending_packages}-${broken})) -ne 0 ]; then
printf '%.1f%% of the planned work has been done.\n' \
"$(
echo "scale=10; 100*(${testing}+${staging})/(${testing}+${staging}+${pending_packages}-${broken})" | \
bc
)" >> \
"${tmp_dir}/build-master-status.html"
fi
if ${web}; then
sed -i 's|$|
|' "${tmp_dir}/build-master-status.html"
end=$(($(date +%s)-7*24*60*60))
(
[ -f "${webserver_directory}/statistics" ] && \
cat "${webserver_directory}/statistics"
printf '%s ' \
"$(date +%s)" \
"${stable}" \
"${tasks}" \
"${pending_packages}" \
"${staging}" \
"${testing}" \
"${broken}" \
"${loops}" \
"${looped_packages}" \
"${locked}" \
"${blocked}" \
"${next_tasks}" | \
sed 's| $|\n|'
echo "${end}"
) | \
sort -k1nr,1 | \
sed -n "
/^${end}\$/q
p
" | \
tac > \
"${tmp_dir}/statistics"
printf '\n
%s | ' \ 'package' \ 'git revision' \ 'modification git revision' \ 'package repository' \ 'compilations' \ 'blocked' >> \ "${tmp_dir}/broken-packages.html" printf '
---|
%s | ' \ ''"${pkg}"'' \ "${rev}" \ "${mod_rev}" \ "${repo}" \ ''"${count}"'' \ "${reason}" printf '