#!/bin/bash set -o errexit set -o nounset set -o pipefail shopt -s lastpipe function join_by { local d=${1-} f=${2-} if shift 2; then printf %s "$f" "${@/#/$d}" fi } results=$(mktemp) cleanup() { rm "$results" } trap cleanup SIGINT SIGHUP SIGABRT EXIT declare -a addresses while read -r key _; do addresses+=("${key%:*}") done ('"$(join_by '|' "${addresses[@]}")"')' < <(zcat /var/log/exim4/mainlog.*.gz) >"$results" declare -Ai domain_names declare -Ai local_names for email in "${addresses[@]}"; do count=$(grep -c '=> '"$email" <"$results") || true IFS='@' read -r local_name domain_name <<<"$email" local_names[$local_name]+=$count domain_names[$domain_name]+=$count done printf '\nTop Local Names:\n' for local_name in "${!local_names[@]}"; do printf '%d\t%s\n' "${local_names[$local_name]}" "$local_name" done | sort -n | tail -n 20 printf '\nTop Domain Names:\n' for domain_name in "${!domain_names[@]}"; do printf '%d\t%s\n' "${domain_names[$domain_name]}" "$domain_name" done | sort -n | tail -n 20