0

My idea is to control the CPU usage of virtual machines through a scheduled task. I have created the following script but I am not sure how to run a function by SSH. Here is the code of my script.

declare -a instances=("INSTANCES-ID")

for ec2instances in ${instances[@]}; do

STATUS=$(aws ec2 describe-instance-status --instance-ids ${ec2instances} | jq '.InstanceStatuses[0].InstanceState.Name')

MAILADDR="email@email"
HOST=$(hostname -s)
TMPFILE=$(mktemp /tmp/info-mail\.XXXXXX)

func_mail2_alert() {
    uptime > ${TMPFILE} 2>&1
    echo -e "\n\n" >> ${TMPFILE}
    echo -e "\n\n" >> ${TMPFILE}
    free -m >> ${TMPFILE} 2>&1
    echo -e "\n\n" >> ${TMPFILE}
    echo -e "TOP - 1" >> ${TMPFILE}
    top -d1 -n1 -b -c -i | head -25 >> ${TMPFILE}
    echo -e "\n\n" >> ${TMPFILE}
    echo -e "TOP - 2" >> ${TMPFILE}
    top -d1 -n1 -b -c -i | head -25 >> ${TMPFILE}
    echo -e "\n\n" >> ${TMPFILE}
    echo -e "PS_MEM\nPrivate  +   Shared  =  RAM used       Program\n" >> ${TMPFILE}
    ps_mem | tail -25 >> ${TMPFILE}
    echo -e "\n\n" >> ${TMPFILE}
    echo "Send Email CPU HIGH"
    LIMITE_MB=5
    LIMITE_B=$[LIMITE_MB*1024*1024]
    if [ `stat --format="%s" ${TMPFILE}` -lt ${LIMITE_B} ] ; then
        cat ${TMPFILE} | mail -s "High CPU on ${HOST}" ${MAILADDR}
    else
        (echo -e "Reporte muy pesado, enviando solo ${LIMITE_MB} MB y comprimiendo ${TMPFILE}\n"
         head --bytes=${LIMITE_B} ${TMPFILE}
        ) | mail -s "Bajando carga en ${HOST}" ${MAILADDR}
        gzip -f ${TMPFILE}
    fi
}

if [ ${STATUS} == "\"running\"" ] ; then

echo -e "Instances running, try ssh connection"

IP_PRIVATE=$(aws ec2 describe-instances --instance-ids "${ec2instances}" | \
jq -r '[.Reservations | .[] | .Instances | .[] | .PrivateIpAddress]' | \
grep -oE '([0-9]{1,3}\.){3}[0-9]{1,3}')

IP_PUBLIC=$(aws ec2 describe-instances --instance-ids "${ec2instances}" | \
jq -r '[.Reservations | .[] | .Instances | .[] | .PublicIpAddress]' | \
grep -oE '([0-9]{1,3}\.){3}[0-9]{1,3}')

SSH_IDENTITY=$HOME/Descargas/cursoaws.pem
SSH_CON=$(ssh -i ${SSH_IDENTITY} -o BatchMode=yes -o ConnectTimeout=10 ec2-user@${IP_PUBLIC} echo ok 2>&1)
SSH_CPU_USAGE=$(ssh -i ${SSH_IDENTITY} ec2-user@${IP_PUBLIC} "cat /proc/loadavg | cut -d ' ' -f2 | cut -d . -f1")

    if [[ "${SSH_CON}" == "ok" ]] ; then
    echo "SSH OK"
        if [[ "${SSH_CPU_USAGE}" -ge 0 ]] ; then
        echo -e "USO de CPU High"
#       ssh -i ${SSH_IDENTITY} ec2-user@${IP_PUBLIC} "$(declare -p TMPFILE HOST MAILADDR ); func_mail2_alert"
        else
        echo -e "CPU normal"
        fi
    fi
    # 
    #Falta generar alerta
#       echo "SSH NO ANDA"
    # Falta generar alerta
else
echo -e "Not responding"
fi

done

In the body of the message I am trying to print some CPU and memory usage values through the function.

How should I run the function? Tried the following way but I saw an ambiguous redirect error:

ssh -i ${SSH_IDENTITY} ec2-user@${IP_PUBLIC} "$(declare -p TMPFILE HOST MAILADDR ); func_mail2_alert"

Any ideas or improvements for my script?

MuzaffarShaikh
  • 380
  • 3
  • 13
pi314
  • 41
  • 2
  • 5
  • 2
    Aside: This is _very_ unnecessarily inefficient code. Putting `>>outfile` on every line over and over opens outfile, runs that line, closes the file, opens the file again, runs the next line, closes it, etc. Much better to do a single redirection with a larger scope. – Charles Duffy Nov 18 '21 at 13:27
  • Anyhow, to pass functions over ssh, use `$(declare -f funcname)` just the same way you pass variables with `$(declare -p varname)`. – Charles Duffy Nov 18 '21 at 13:28
  • 1
    (also, in general, `echo -e` should not be used at all, ever, by anyone; see the APPLICATION USAGE and RATIONALE sections of [the POSIX specification for `echo`](https://pubs.opengroup.org/onlinepubs/9699919799/utilities/echo.html), and the excellent [unix.se] question [Why is printf better than echo?](https://unix.stackexchange.com/a/65819/3113)) – Charles Duffy Nov 18 '21 at 13:30
  • 1
    (also, POSIX reserves all-caps variables for use by the shell and standard tools; applications have names with at least one lower-case character reserved for their use; lowercase names are guaranteed not to have unintended side effects on POSIX-standardized tools. See the relevant standard document at https://pubs.opengroup.org/onlinepubs/9699919799/basedefs/V1_chap08.html, keeping in mind that setting a shell variable overwrites any like-named environment variable, so the conventions apply across both environment variables and shell variables) – Charles Duffy Nov 18 '21 at 13:32

0 Answers0