I made this motd script:
#!/bin/bash
# Calulate avg CPU usage
usage=$((100-$(vmstat 1 2|tail -1|awk '{print $15}')))
aptlist=$(apt list --upgradable 2> /dev/null | sed 1d)
# Check if current usage isn't to high, else don't display the motd
if [[ ${usage%.*} -ge 95 ]];
then
printf "motd disabled because current usage is %sn" "$usage"
else
# The magic
date=$(date)
# usage=$(tail /proc/loadavg | awk '{print $1}')
root_usage=$(df -h / | awk '/// {print $(NF-1)}')
# memory_usage=$(free -m | grep Mem | awk '{print 100/$2*($2-$6+$5)}' | xargs printf "$1""%.2f")
memory_usage=$(printf "%0.2f MB %d%%n" $(( $(sed -E '/^(MemTotal|MemFree|Cached|Buffers): *([0-9]*).*/'
'{s//2/;H;};$!d;x;s/[[:cntrl:]]//;s__/1024-_g;s_$_/1024_' /proc/meminfo) ))
$(( $(sed -E '/^(MemTotal|MemFree|Cached|Buffers): *([0-9]*).*/'
'{s//2/;H;};$!d;x;s/[[:cntrl:]]//;s_([^n]+)n_@1@100*(1/1024-(_;s_n_/1024+_g;'
's_@([^@]+)@(.*)$_2/1024))/(1/1024)_' /proc/meminfo) )) | awk '{print $3}')
users=$(users | wc -w)
time=$(uptime | grep -ohe 'up .*' | sed 's/,/ hours/g' | awk '{ printf $2" "$3 }')
processes=$(ps aux | wc -l)
ip=$(ip addr | awk '/inet / { print $2 }' | sed -n '2{p;q}' | cut -d '/' -f1)
ipv6=$(ip -6 addr |awk '{print $2}'| grep -v "^::" | grep "/" | head -n1 | cut -d '/' -f1)
packages=$(dpkg-query -l | grep -c "^ii")
updates=$(echo -n $aptlist | wc -l )
secupdates=$(echo $aptlist | grep -c security )
# The updates and secupdates var get's it's info thanks to this crontab/command
# sudo apt-get -s dist-upgrade | grep "^Inst" | wc -l > /etc/update-motd.d/pkg.stats && apt-get -s dist-upgrade | grep "^Inst" | grep -i security | wc -l >> /etc/update-motd.d/pkg.stats
# sudo crontab -l | { cat; echo "0 0 * * * apt-get -s dist-upgrade | grep "^Inst" | wc -l > /etc/update-motd.d/pkg.stats && apt-get -s dist-upgrade | grep "^Inst" | grep -i security | wc -l >> /etc/update-motd.d/pkg.stats"; } | crontab -
# If you wish to not use crontab, switch the updates and secupdates comment's.
# Header & motd
printf "Welcome to %s (%s)" "$(lsb_release -s -d)" "$(uname -rm)"
printf "n"
echo " __ __ __ _ __ _______"
echo " / //_/ / /(_)/ /__ ____ |_____|"
echo " / ,< / // // //_// __ | │ │ |"
echo " / /| | / // // ,< / /_/ / | |"
echo " /_/ |_|/_//_//_/|_| ____/ ◯_____| "
echo
# System information
echo "System information as of: $date"
echo
# printf "System Load:t%stSystem Uptime:t%sn" "$load" "$time" # Use this one if you prefer the linux proc avg
printf "System Load:t%s%%tSystem Uptime:t%sn" "$usage" "$time" # Overall processor usage
printf "Memory Usage:t%stIP Address:t%sn" "$memory_usage" "$ip"
if [[ $ipv6 == "" ]]
then
printf "Usage On /:t%stIPv6 Addres:tNo ipv6 address foundn" "$root_usage"
else
printf "Usage On /:t%stIPv6 Addres:t%sn" "$root_usage" "$ipv6"
fi
printf "Local Users:t%stProcesses:t%sn" "$users" "$processes"
printf "Packages dpkg:t%stSession fortune: nn" "$packages"
/usr/games/fortune
# Check if there are updates
echo
if [[ $updates != 0 ]]
then
printf "%s updates can be installed immediately.n" "$updates"
printf "%s of these updates are security updates.n" "$secupdates"
printf "To see these additional updates run: apt list --upgradablenn"
else
printf "System is up-to-date!nn"
fi
# Check if a reboot is needed
if [[ -f /var/run/reboot-required ]]
then
echo '*** System restart required ***'
fi
fi
printf "%s" "$aptlist"
Now the execution time is 2 seconds b/c of these two commands:
usage=$((100-$(vmstat 1 2|tail -1|awk '{print $15}')))
aptlist=$(apt list --upgradable 2> /dev/null | sed 1d)
I tried to find a way to run both of the commands at the same time, so that it only takes a second (which would be amazing). Sadly using var1=cmd1 & var2=cmd2 doesn’t work and only the second get’s executed properly.
Anyone has a clue how to run two commands that go into each of their variables at the same time?
(i prefer to use the default tools in debian/Raspberry but if it’s impossible, i’m ok to install that package :))
Thank you for reading!
3
Answers
One approach:
wait
For example:
NOTE: OP could add any necessary error checking after the
wait
and before theusage=$((...)); read -r aptlist ...
commandsuse a dummy single-cycle
for
loop as a proxy for waiting :As for ur commands, u can streamline them into
and
UPDATE 1 : trying another approach
As a variant on markp-fuso’s answer that avoids the need for temporary files by using process substitutions and automatic FD allocation (and is thus expected to work only with newer bash 4.x releases, or all bash 5.0+ releases):