My if statement doesn't work why?

I have the following and for some reason I can't have two options together.
I mean if I choose -u and -p it won't work... why?

#!/bin/bash

resetTime=1
mytotalTime=0
totalHour=0
totalMin=0
averagemem=0
finalaverage=0
times=0
function usage()
{
cat << EOF

USAGE: $0 [options] file

EOF
}

function usageOption()
{
cat << EOF

$0 Must select report type: -u(ser) or -c(ommand)

EOF
}

function displayTime() {
    awk -F"," '/'$user'/{print $7}' $file > /tmp/mytotalTime.$USER
    cat /tmp/mytotalTime.$USER | while read resetTime;
    do
        Min=$(echo $resetTime | cut -d ":" -f2)
        Hour=$(echo $resetTime | cut -d ":" -f1)
        totalHour=$((totalHour+Hour))
        echo $totalHour > /tmp/totalHour.$USER
        totalMin=$(echo "($totalMin+$Min)" | bc) 
        echo $totalMin > /tmp/totalMin.$USER
    done
    totalHour=$(cat /tmp/totalHour.$USER)
    totalMin=$(cat /tmp/totalMin.$USER)
    mytotalTime=$(echo "($totalHour*60+$totalMin)" | bc)
    totalHour=$(echo "($mytotalTime/60)" | bc)
    totalMin=$(echo "($mytotalTime%60)" | bc)
    echo -e "TOTAL RUNNING TIME:    " $totalHour":"$totalMin "\n"
}

if [ $# -eq 0 ]; then
    usage
    exit 1
fi

user=
command=
fileName=
totalTime=
memoryUse=
priority=
OPTIND=1    # Reset in case getopts has been used previously in the shell

while getopts "u:c:f:tmp" opt;do
 case $opt in
    u)    user=$OPTARG;[ OPTIND=${OPTIND} ];uflag=$user;;
    c)    mycommand=$OPTARG;[ OPTIND=${OPTIND} ]; echo $OPTIND;;
    f)    fileName=$OPTARG;echo "$fileName";[ OPTIND=${OPTIND} ]; echo $OPTIND;;
    t)    totalTime=$OPTARG;[ OPTIND=${OPTIND} ]; echo $OPTIND;;
    m)    memoryUse=$OPTARG;echo "$memoryUse";[ OPTIND=${OPTIND} ];;
    p)    priority=OPTARG;[ OPTIND=${OPTIND} ];;
    \?)    usage;exit 1;;
    *)        echo -e "\nOption -$OPTARG requires an argument.\n";exit 1;;
 esac
done
shift $(($OPTIND - 1))

# Check for proper number of command line args.

EXPECTED_ARGS=1
#E_BADARGS=65

if [ $# -ne $EXPECTED_ARGS ]; then
    usage
    exit 1
 #exit $E_BADARGS
fi

if [ $user ] && [ $mycommand ]; then
    usageOption
    exit 1
elif [ ! -f $1 ]; then
    usage
    exit 1
elif [ $# -ge 2 ]; then
    usage
    exit 1
elif [ -z $user ] && [ -z $mycommand ]; then
    usageOption
    exit 1
fi
file=$1

if [ user ]; then
    printf "\nTOP ANALYSIS REPORT\n"
    printf "\nName: %4s\n" $user

    if [ pflag ]; then
        echo "-------------------------------------------------------------------------------------------------"
        printf "| %-15s | %-23s | %-10s | %-10s | %-10s | %-10s |\n" "USER" "PROCESS" "PROC ID" "% CPU" "% MEM" "PRIORITY"
        echo "|-----------------+-------------------------+------------+------------+------------+------------|"
        awk -F"," '/'$user'/ { printf "| %-15s | %-23s | %-10s | %-10s | %-10s | %-10s |\n", $2, $3, $1, $5, $6, $4 }' $file
        echo "-------------------------------------------------------------------------------------------------"
    else
        echo "------------------------------------------------------------------------------------"
        printf "| %-15s | %-23s | %-10s | %-10s | %-10s |\n" "USER" "PROCESS" "PROC ID" "% CPU" "% MEM"
        echo -e "|-----------------+-------------------------+------------+------------+------------|"
        awk -F"," '/'$user'/ { printf "| %-15s | %-23s | %-10s | %-10s | %-10s |\n", $2, $3, $1, $5, $6 }' $file
        echo -e "------------------------------------------------------------------------------------"


 fi
fi

I didn't look very closely, but it looks like you are missing a dollar sign in this statement:

    p)    priority=OPTARG;[ OPTIND=${OPTIND} ];;

Should be (I think):

    p)    priority=$OPTARG;[ OPTIND=${OPTIND} ];;

I didn't look to see if this was your only issue, but it is where I would start. Change and have a go with it.

Thanks for taking your time on this.
When I run:

this is what I get as the output is:

But it shouldn't give the priority column without -p command in the terminal. do you know why I get this??

You need to dereference your variables when you use them as a part of a test expression.


if [ $user ]; then

and

if [ $pflag ]; then

Both need to have $varname and not just varname.

So, you mean something like this:

if [ $user ]; then
    printf "\nTOP ANALYSIS REPORT\n"
    printf "\nName: %4s\n" $user

    if [ $mycommand ]; then
        echo "-------------------------------------------------------------------------------------------------"
        printf "| %-15s | %-23s | %-10s | %-10s | %-10s | %-10s |\n" "USER" "PROCESS" "PROC ID" "% CPU" "% MEM" "PRIORITY"
        echo "|-----------------+-------------------------+------------+------------+------------+------------|"
        awk -F"," '/'$user'/ { printf "| %-15s | %-23s | %-10s | %-10s | %-10s | %-10s |\n", $2, $3, $1, $5, $6, $4 }' $file
        echo "-------------------------------------------------------------------------------------------------"
 fi
  else       echo "------------------------------------------------------------------------------------"
        printf "| %-15s | %-23s | %-10s | %-10s | %-10s |\n" "USER" "PROCESS" "PROC ID" "% CPU" "% MEM"
        echo -e "|-----------------+-------------------------+------------+------------+------------|"
        awk -F"," '/'$user'/ { printf "| %-15s | %-23s | %-10s | %-10s | %-10s |\n", $2, $3, $1, $5, $6 }' $file
        echo -e "------------------------------------------------------------------------------------"

fi

Believe me, I tried this as well. It doesn't work. I am totally lost! :frowning:
This is the output:

That looks correct if you only have -u and -p (at least, since you re-structured the if statements...).

I am going to cry my eyes out! this damn script doesn't work and I can't see my mistakes! I think everything is OK but if user choose two options, the output won't be correct!:wall:

I had a closer look at your script (before I only looked at the statements that you pointed out). The problem is that you are testing pflag but never setting it. Your statement when gathering options probably should be:

 p)    pflag=1;  [ OPTIND=${OPTIND} ];;

If I were writing the script, I would initialise it to zero, and specifically test for it being greater than zero which would work with the above code.

if [ $pflag -gt 0 ]        # -p was set on command line

I also think that you need to quote your variables when testing using -n or -z within single brackets. For example:

if [ -z "$user" ]

I also prefer to specifically use -n when testing to see if a string (contents of a variable) has size:

if [ -n "$user" ]

even though the following might work in some shells:

if [ $user ]

Hope this gets you further.

Thanks

Implementing the suggestions I made before, this works fine for me:

#!/bin/bash

resetTime=1
mytotalTime=0
totalHour=0
totalMin=0
averagemem=0
finalaverage=0
times=0
function usage
{
    cat << EOF
    USAGE: $0 [options] file
EOF
}

function usageOption
{
    cat << EOF
    $0 Must select report type: -u(ser) or -c(ommand)
EOF
}

function displayTime
{
    awk -F"," '/'$user'/{print $7}' $file > /tmp/mytotalTime.$USER
    cat /tmp/mytotalTime.$USER | while read resetTime;
    do
        Min=$(echo $resetTime | cut -d ":" -f2)
        Hour=$(echo $resetTime | cut -d ":" -f1)
        totalHour=$((totalHour+Hour))
        echo $totalHour > /tmp/totalHour.$USER
        totalMin=$(echo "($totalMin+$Min)" | bc)
        echo $totalMin > /tmp/totalMin.$USER
    done
    totalHour=$(cat /tmp/totalHour.$USER)
    totalMin=$(cat /tmp/totalMin.$USER)
    mytotalTime=$(echo "($totalHour*60+$totalMin)" | bc)
    totalHour=$(echo "($mytotalTime/60)" | bc)
    totalMin=$(echo "($mytotalTime%60)" | bc)
    echo -e "TOTAL RUNNING TIME:    " $totalHour":"$totalMin "\n"
}

if [ $# -eq 0 ]; then
    usage
    exit 1
fi

pflag=
user=""
command=
fileName=
totalTime=
memoryUse=
priority=
OPTIND=1    # Reset in case getopts has been used previously in the shell

while getopts "u:c:f:tmp" opt;do
 case $opt in
    u)    user=$OPTARG;[ OPTIND=${OPTIND} ];uflag=$user;;
    c)    mycommand=$OPTARG;[ OPTIND=${OPTIND} ]; echo $OPTIND;;
    f)    fileName=$OPTARG;echo "$fileName";[ OPTIND=${OPTIND} ]; echo $OPTIND;;
    t)    totalTime=$OPTARG;[ OPTIND=${OPTIND} ]; echo $OPTIND;;
    m)    memoryUse=$OPTARG;echo "$memoryUse";[ OPTIND=${OPTIND} ];;
    p)    pflag=1;  [ OPTIND=${OPTIND} ];;
    \?)    usage;exit 1;;
    *)        echo -e "\nOption -$OPTARG requires an argument.\n";exit 1;;
 esac
done
shift $(($OPTIND - 1))

# Check for proper number of command line args.

EXPECTED_ARGS=1
#E_BADARGS=65

if [ $# -ne $EXPECTED_ARGS ]; then
    usage
    exit 1
 #exit $E_BADARGS
fi

if [ -n "$user" ] && [ -n "$mycommand" ]; then
    usageOption
    exit 1

elif [ ! -f $1 ]; then
    usage
    exit 1
elif [ $# -ge 2 ]; then
    usage
    exit 1
elif [ -z "$user" ] && [ -z "$mycommand" ]; then
    usageOption
    exit 1
fi

file=$1

if [  -n "$user" ]
then
    printf "\nTOP ANALYSIS REPORT\n"
    printf "\nName: %4s\n" $user

    if [ $pflag  ]; then        ###
        echo "-------------------------------------------------------------------------------------------------"
        printf "| %-15s | %-23s | %-10s | %-10s | %-10s | %-10s |\n" "USER" "PROCESS" "PROC ID" "% CPU" "% MEM" "PRIORITY"
        echo "|-----------------+-------------------------+------------+------------+------------+------------|"
        awk -F"," '/'$user'/ { printf "| %-15s | %-23s | %-10s | %-10s | %-10s | %-10s |\n", $2, $3, $1, $5, $6, $4 }' $file
        echo "-------------------------------------------------------------------------------------------------"
    else
        echo "------------------------------------------------------------------------------------"
        printf "| %-15s | %-23s | %-10s | %-10s | %-10s |\n" "USER" "PROCESS" "PROC ID" "% CPU" "% MEM"
        echo -e "|-----------------+-------------------------+------------+------------+------------|"
        awk -F"," '/'$user'/ { printf "| %-15s | %-23s | %-10s | %-10s | %-10s |\n", $2, $3, $1, $5, $6 }' $file
        echo -e "------------------------------------------------------------------------------------"
   fi
fi

1 Like

THANK YOU SOOOOO MUCH!!!! You are the best. I have nothing to say. WELL DONE!!:b:;):eek: