#!/bin/sh

# Copyright © 2009-2018 Holger Levsen (holger@layer-acht.org)
# Copyright © 2011-2019 Andreas Beckmann (anbe@debian.org)
#
# This program is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by the
# Free Software Foundation; either version 2 of the License, or (at your
# option) any later version.
#
# This program is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
# Public License for more details.
#
# You should have received a copy of the GNU General Public License along
# with this program. If not, see <https://www.gnu.org/licenses/>


. /usr/share/piuparts/lib/read_config.sh
. /usr/share/piuparts/lib/write_log.sh

get_config_value MASTER global master-directory
get_config_value SECTIONS global sections
get_config_value HTDOCS global output-directory

STARTDATE=$(date -u +%s)
LOG_OUTPUT=$(mktemp)
LOG_PREFIX=$(mktemp)

#
# detect piuparts problems
#

newline="
"
tab="	"
PATTERN=
DISPLAY_PATTERN=

add_pattern()
{
	PATTERN="${PATTERN:+${PATTERN}|}($1)"
	DISPLAY_PATTERN="${DISPLAY_PATTERN:+${DISPLAY_PATTERN}${newline}}${tab}$1"
}

add_pattern 'PIUPARTS OUTPUT INCOMPLETE'
add_pattern "WARNING: History of available packages does not match - reference chroot may be outdated"
add_pattern "tar( \(child\))?: .*.tar.gz: Cannot open: No such file or directory"
add_pattern "tar: Error is not recoverable: exiting now"
add_pattern "gzip: stdin: invalid compressed data--crc error"
add_pattern "ERROR:.*:Temporary directory is not a directory"
add_pattern "E: Sub-process Popen returned an error code \(2\)"
add_pattern "chroot: failed to run command '.*': Permission denied"
add_pattern "ERROR: Command failed \(status=(-7|100)\): .* 'apt-cache'"
add_pattern 'update-binfmts: warning: unable to close /proc/sys/fs/binfmt_misc/register: Invalid argument'
add_pattern 'USERDEL: USER .* IS CURRENTLY LOGGED IN'
add_pattern 'userdel: user .* is currently logged in'
add_pattern 'mount: .* Cannot allocate memory'
# Disk space issues.
add_pattern "NO SPACE LEFT ON DEVICE"
add_pattern "No space left on device"
add_pattern "E: You don't have enough free space in /var/cache/apt/archives/"
add_pattern "E: Failed to write temporary StateFile /var/lib/apt/extended_states.tmp"
add_pattern "tar: .*: Wrote only .* of .* bytes"
add_pattern "sh: echo: I/O error"
add_pattern "passwd: Authentication token manipulation error"
add_pattern "(chfn|groupadd|useradd): (cannot lock|failure while writing changes to) /etc/(group|gshadow|passwd|shadow|subuid)"
add_pattern "(groupadd|useradd): (unable to lock|cannot rewrite) (group|password) file"
# Database server issues.
add_pattern 'INVOKE-RC.D: INITSCRIPT (MYSQL|POSTGRESQL|POSTGRESQL-8.3), ACTION "(RE)?START" FAILED.'
add_pattern 'invoke-rc.d: initscript (mariadb|mysql|postgresql|postgresql-8.3), action "(re)?start" failed.'
add_pattern 'There is a MySQL server running, but we failed in our attempts to stop it.'
add_pattern 'The PostgreSQL server failed to start.'
add_pattern 'Is another postmaster already running on port 543.'
add_pattern 'No database found online on port 5432'
add_pattern 'unable to connect to postgresql server'
add_pattern 'Failed to connect to postgres.'
add_pattern 'PG::ConnectionBad: could not connect to server'
add_pattern 'psql: FATAL:  password authentication failed for user'
add_pattern 'createuser: could not connect to database postgres: could not connect to server: No such file or directory'
add_pattern 'Non-default port in /etc/postgresql/.*/main/postgresql.conf'
add_pattern 'Firebird .* server already running.'
# These are python errors from piuparts itself. Python errors from maintainer
# scripts etc. would be indented by 2 spaces, so don't match here.
add_pattern "^RuntimeError: maximum recursion depth exceeded while calling a Python object"
add_pattern "^Traceback"
add_pattern "^IndentationError:"
add_pattern "^NameError:"
add_pattern "^OSError:"
add_pattern "^SyntaxError:"

FILE=$(mktemp)
for SECTION in $SECTIONS ; do
	test -d $MASTER/$SECTION || continue
	for subdir in fail bugged affected ; do
		test -d $MASTER/$SECTION/$subdir || continue
		grep -r -l -E --include '*.log' "$PATTERN" $MASTER/$SECTION/$subdir >> $FILE 2>/dev/null
	done
	for subdir in fail bugged affected untestable pass ; do
		test -d $MASTER/$SECTION/$subdir || continue
		find $MASTER/$SECTION/$subdir -name 'tmp??????' -mtime +1 -delete 2>/dev/null
		find $MASTER/$SECTION/$subdir -name '*.log' -size 0 >> $FILE
	done
done
if [ -s $FILE ] ; then
	FINALDATE=$(date -u +%s)
	RUNTIME=$(date -u -d "0 $FINALDATE seconds - $STARTDATE seconds" +%T)
	(
		echo "piuparts problems detected! Please review the following logfiles/packages."
		echo "If it is always the same package failing, it's likely to be an issue in the"
		echo "package."
		echo
		echo "Problems were found in failed logs by grep'ing for these patterns:"
		echo "$DISPLAY_PATTERN"
		echo
	) > $LOG_PREFIX
	(
		echo "$(date -u)"
		echo "Runtime: $RUNTIME"
		echo
		echo "The following logfiles have been deleted:"
		echo
		for log in $(sort -u $FILE)
		do
			echo "$log" | cut -d "/" -f5-
			test -s "$log" || echo "${tab}Empty logfile."
			grep -E "$PATTERN" "$log" 2>/dev/null | perl -e 'print grep !$seen{$_}++, <>;' | head -n 10 | sed "s/^/${tab}/"
			rm -f "$log"
		done
		echo
	) > $LOG_OUTPUT
	publish_logs $LOG_OUTPUT $LOG_PREFIX $HTDOCS piuparts_issues
fi
rm $FILE
