Nk_sarmaxes

Home

TODO truncate seconds.

We don’t need seconds in the results, it’s just clutter.

Description

This bash function, nk_sarmaxes(), is a wrapper function around gen_sarmaxes that formats the output of gen_sarmaxes into columns to make it more readable. The script uses several functions to generate a list of all sar log files available, determine the date of the file, find the maximum load and memory usage for each log file, and print out the results in a formatted table. The table contains columns for the date, the timestamp of the maximum load, the maximum load, the timestamp of the maximum memory usage, and the maximum memory usage. The output is sorted in reverse order by date, with the most recent date at the top. Finally, the output is piped through the column command to format it into columns.

Example

[root@cloudvpsserver ~]# nk_sarmaxes 
Date        │  Load_Timestamp  Load_Max  Load-%  │  Mem_Timestamp  Mem_Max  Mem-%    │
2023-04-12  │  08:00:01:PM     0.42      21%     │  04:10:01:PM    923MB    77.76%   │
2023-04-11  │  02:00:00:PM     0.97      48.5%   │  02:00:01:AM    893MB    74.62%   │
2023-04-10  │  07:30:01:AM     0.23      11.5%   │  04:50:00:PM    1.1GB    74.96%   │
2023-04-09  │  09:10:01:PM     0.49      24.5%   │  06:00:01:PM    969MB    73.61%   │
2023-04-08  │  04:00:00:PM     1.56      78%     │  06:10:01:PM    957MB    78.90%   │
2023-04-07  │  02:30:01:AM     0.65      32.5%   │  05:40:00:PM    1002MB   74.92%   │
2023-04-06  │  11:20:01:PM     0.91      45.5%   │  05:50:00:PM    996MB    76.31%   │
2023-04-05  │  09:20:01:AM     0.87      43.5%   │  04:50:01:PM    965MB    74.49%   │
2023-04-04  │  11:40:00:AM     0.69      34.5%   │  04:00:01:PM    987MB    73.15%   │

Code

nk_sarmaxes() {
# nk_sarmaxes is essentially just a wrapper around gen_sarmaxes() that formats it into columns so it looks pretty.
cores=$(nproc)
    ### First we have to define some functions to be used later ###
alma_bool="$(grep -c "AlmaLinux" /etc/redhat-release)"

gen_sa_list() {
# This generates a list of all the sar log files available.
# Sar logs are stored as /var/log/sa/sa01 where the numeric value is the day of the month
find /var/log/sa/ | grep -E "sa[0-9][0-9]"
}

find_day() {
# Sar logs don't contain the date in them only timestamps.
# So we need a way to determine the date of the file we're currently working on
# Luckily we can just run a stat on the file and grab the modified date.
    stat -c "%y" "$safile" | awk '{print $1}'
}

find_load_max_timestamp() {
# First we run sar -q -f  on the active sar file.
# Then remove any header or restart info. So we just have numeric values.
# Sort descending on column 5 (which is 5 min load average)
# Take the top one which will be the highest load.
# Output columns 1 and 2 from the top line, which will be the timestamp.
    sar -q -f "$safile" | grep -Ev "(Average|runq|Linux|RESTART)" | sort -r -k 5 | head -1 | awk '{print $1":"$2}'
}

find_load_max() {
# First we run sar -q -f  on the active sar file.
# Then remove any header or restart info. So we just have numeric values.
# Sort descending on column 5 (which is 5 min load average)
# Take the top one which will be the highest load.
# Output column 5 which is the top 5 minute load of the day.
    sar -q -f "$safile" | grep -Ev "(Average|runq|Linux|RESTART)" | sort -r -k 5 | head -1 | awk '{print $5}'
}

find_mem_max_timestamp() {
# First we run sar -r -f  on the active sar file.
# Then remove any header or restart info. So we just have numeric values.
# Sort descending on column 9 (which is percent kbmemcommit)
# Take the top one which will be the highest memcommit.
# Output columns 1 and 2 from the top line which will be the timestamp.
    sar -r -f "$safile" | grep -Ev "(Average|Linux|kbmem|RESTART)" | sort -rn -k 9 | head -1 | awk '{print $1":"$2}'
}

find_mem_max() {
# First we run sar -r -f  on the active sar file.
# Then remove any header or restart info. So we just have numeric values.
# Sort descending on column 9 (which is percent kbmemcommit)
# Take the top one which will be the highest memcommit.
# Output column 9 which is the max kbmem commit.
if [ "$alma_bool" = "1" ]; then
    mem_max_percent="$(sar -r -f "$safile" | grep -Ev "(Average|Linux|kbmem|RESTART)" | sort -rn -k 9 | head -1 | awk '{print $10}')"
    mem_max_kb="$(sar -r -f "$safile" | grep -Ev "(Average|Linux|kbmem|RESTART)" | sort -rn -k 9 | head -1 | awk '{print $4}')"
    mem_max_bytes="$(echo "$mem_max_kb" | awk '{print $1*1000}')"
    mem_max_human="$(numfmt --to=iec --suffix=B "$mem_max_bytes")"
    echo "$mem_max_human $mem_max_percent%"
    return 0
fi
    sar -r -f "$safile" | grep -Ev "(Average|Linux|kbmem|RESTART)" | sort -rn -k 9 | head -1 | awk '{print $9}'
}

### Now it all starts to come together.

gen_sarmaxes() {
# First  we print the header for the table.
echo "Date │ Load_Timestamp Load_Max Load-% │ Mem_Timestamp Mem_Max Mem-% │"
# Now for every sar log file that we find with gen_sa_list, define values and print them.
for safile in $(gen_sa_list); do
    # We use the functions defined earlier to populate values for each of these variables.
    day="$(find_day)"
    load_max_timestamp="$(find_load_max_timestamp)"
    load_max="$(find_load_max)"
    load_percent="$(nk_percent "$load_max" "$cores")"
    load_result="$load_max $load_percent"
    mem_max_timestamp="$(find_mem_max_timestamp)"
    mem_max="$(find_mem_max)"

    # And then print them out, arranged just like the header.
    echo "$day$load_max_timestamp $load_result$mem_max_timestamp $mem_max │"
done | sort -rn
# Once the table contents have been populated, sort them in reverse order.
# This makes it so that the most recent date is at the top.
}

# Finally, run it all and format it.
gen_sarmaxes | column -t
}

Author: Nichole Kernreicht

Created: 2023-04-12 Wed 21:44