#!/bin/bash
#---------------------------------*- sh -*-------------------------------------
# ==  == ====== ====   ====    |
#                   \\     ||  | Multiphase Code Repository by HZDR
# ======   //   ||  || ===//   | Website: https://doi.org/10.14278/rodare.767
# ||  ||  //    ||  // || \\   | License: GPL-3.0-or-later
# ==  == ====== ====   ==  ==  |
#------------------------------------------------------------------------------
# License
#     This file is part of the Multiphase Code Repository by HZDR.
#
#     Copyright (C) 2025 by Helmholtz-Zentrum Dresden-Rossendorf e.V. (HZDR),
#     Website: https://hzdr.de
#
#     Multiphase Code Repository by HZDR is based on the free software for
#     computational fluid dynamics (CFD) from the OpenFOAM Foundation.
#     Copyright (C) 2025 by OpenFOAM Foundation, Website: https://openfoam.org
#
#     If you are interested in which files are original OpenFOAM Foundation
#     files, which OpenFOAM Foundation files were modified, and which files were
#     newly created, see FILES.md.
#
#     Multiphase Code Repository by HZDR 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 3 of the
#     License, or (at your option) any later version.
#
#     Multiphase Code Repository by HZDR 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 the Multiphase Code Repository by HZDR. If not, see
#     <http://www.gnu.org/licenses/>.
#
# Description
#     Extract residuals over pimple loops from log file into dat file,
#     independent from runTime
#
#------------------------------------------------------------------------------

PROGNAME=$(basename "$0")
FORCE=false

usage() {
   while [ "$#" -ge 1 ]; do echo "$1"; shift; done
   cat<<USAGE

usage: $PROGNAME [OPTION] LOGFILE

options:
  -f | --force  overwrite existing data file
  -n#           number of PIMPLE loops at the end of LOGFILE to extract from
  -h | --help   this usage

* Extract initial residuals over pimple loops from log file into dat file:
  ./postProcessing/pimpleResiduals/pimpleResiduals.dat

USAGE
   exit 1
}

# Parse options
NTAILS=False
while [ "$#" -gt 0 ]
do
   case "$1" in
   -h | --help)
      usage
      ;;
   -f | --force)
      FORCE=true
      shift
      ;;
   -n[0-9]*)
      NTAILS=${1//-n/}
      [[ ! $NTAILS =~ ^-?[0-9]+$ ]] && usage "Error: invalid option '$1'"
      shift
      ;;
   -*)
      usage "Error: Invalid option '$1'"
      ;;
   *)
      break
      ;;
   esac
done

# Create some default variables
[ -z "$1" ] && usage "Error: No log file given" || LOGFILE=$1
PWD=$(pwd)
DATPATH="postProcessing/pimpleResiduals"
DATFILE=$DATPATH"/pimpleResiduals.dat"
TMP="log.tmp"

# Check log file and copy to tmp file
if [ ! -f "$PWD/$LOGFILE" ]; then
    usage "Error: Log file does not exist:\n  $LOGFILE"
else
    cp "$PWD/$LOGFILE" "$PWD/$TMP"
fi

# Remove old files
if [ "$FORCE" == "true" ] && [ -f "$PWD/$DATFILE" ]; then
    echo "  Removing old dat file"
    rm -f "$PWD/$DATFILE"
fi

# Create directories
if [ ! -d $DATPATH ]; then
    echo "  Creating directory "$DATPATH
    mkdir -p $DATPATH
fi

# Parse solution variables
# Attention: grep require revision to avoid shellcheck warning
#            https://www.shellcheck.net/wiki/SC2207
# shellcheck disable=SC2207
VARIABLES=($(grep "Solving for " $TMP | grep -v "MULES" | grep -v "nonePCG"| \
    head -1000 | sed 's/.*for //' | sed 's/, Initial.*/ /'))
VARS=()
for i in $(seq 1 ${#VARIABLES[@]}); do
    VAR=${VARIABLES[i-1]}

    PRESENT=False
    for item in "${VARS[@]}"; do
        [[ $VAR == "$item" ]] && PRESENT=True
    done
    [[ $PRESENT = True ]] && break

    VARS+=("$VAR")
done

# Reading residuals from log file
declare -A RESIDUALS
NUMMIN=False
for i in $(seq 1 ${#VARS[@]}); do
    VAR=${VARS[i-1]}
    if [[ $NTAILS = False ]]; then
        # shellcheck disable=SC2207
        RES=($(grep "Solving for $VAR" $TMP | \
            sed 's/.*, Initial residual = / /'| sed 's/, Final.*//'))
    else
        # shellcheck disable=SC2207
        RES=($(grep "Solving for $VAR" $TMP | tail -"$NTAILS" | \
            sed 's/.*, Initial residual = / /'| sed 's/, Final.*//'))
    fi

    NUM=${#RES[@]}
    if [[ $NUMMIN = False ]]; then
        NUMMIN=$NUM
    else
        if [ "$NUM" -lt "$NUMMIN" ]; then
            NUMMIN=$NUM
        fi
    fi

    echo "  Reading residuals for variable $VAR"
    for j in $(seq 1 "$NUM"); do
        RESIDUALS["${i-1} ${j-1}"]=${RES[j-1]}
    done
done

# Create dat file
if [ -f "$PWD/$DATFILE" ]; then
    usage "Error: Dat file exists but must not be overwritten either"
else
    echo "  Creating "$DATFILE

    echo -n "#" >> "$PWD/$DATFILE"
    for i in $(seq 0 ${#VARS}); do
        echo -n " ${VARS[i]}" >> "$PWD/$DATFILE"
    done
    echo >> "$PWD/$DATFILE"

    for j in $(seq 1 "$NUM"); do
        for i in $(seq 1 ${#VARS[@]}); do
            echo -n " ${RESIDUALS["${i-1} ${j-1}"]}" >> "$PWD/$DATFILE"
        done
        echo >> "$PWD/$DATFILE"
    done
fi

# Remove tmp file
rm "$PWD/$TMP"

# Exit
echo "  Done"
exit 0

#------------------------------------------------------------------------------
