Whats wrong with if statement in shell script - shell

Here is my statements:
print "Ss $# $2" >&3
if [ $# -eq 4 || $# -eq 3 ] && [ $2 != "d" ]
then
print "sss"
else
print "lol"
fi
The output is:
Ss 4 s
lol
Why is "sss" not being displayed?

Your if-condition isn't syntactically correct. You can't have || inside the brackets. Change it to use -o instead:
if [ $# -eq 4 -o $# -eq 3 ] && [ $2 != "d" ]
then
print "sss"
else
print "lol"
fi
Or, even better, use [[ (if your shell supports it) which is safer and has more features. It supports ||:
if [[ ( $# -eq 4 || $# -eq 3 ) && $2 != "d" ]]
then
print "sss"
else
print "lol"
fi

Related

Bash detect 1st input parameter is "debug"?

I want to detect if the 1st bash input parameter is "debug"(string).
I write script like this:
#! /usr/bin/env bash
if [ "$#" -eq "1" && "$1" -eq "debug" ]; then
echo "hello debug"
fi
Error message:
line 3: [: missing `]'
I don't know why, please help.
Compare strings with ==, -eq is an arithmetic operator. Also, within [] you have to use the -a operator instead of &&, or split it in two. Here are a few different ways to write the same thing:
if [[ $# -eq 1 && "$1" == "debug" ]] ; then
echo "hello debug"
fi
if [[ "$#" == "1" && "$1" == "debug" ]] ; then
echo "hello debug"
fi
if [ "$#" == "1" ] && [ "$1" == "debug" ] ; then
echo "hello debug"
fi
if [ "$#" == "1" -a "$1" == "debug" ] ; then
echo "hello debug"
fi
Instead of [ "$#" -eq "1" && "$1" -eq "debug" ], use either [ "$#" -eq "1" ] && [ "$1" -eq "debug" ] or [ "$#" -eq "1" -a "$1" -eq "debug" ]. The problem is that && is bash's way of saying "and", rather than -a, which is test's way of saying "and". You can't use a bash "and" inside of test.

How to use multiple condition in if statement in bash?

Actually I am a new bash learner. I can use one condition in bash command. But how to use multiple condition in bash? I can use if statement like this:
read a
if [ $a = "y" ] ; then
echo "YES"
elif [ $a = "Y" ] ; then
echo "YES"
else
echo "NO"
fi
I am finding something like this:
read a b c
if [ $a -eq $b and $b -eq $c ] ; then
echo "EQUILATERAL"
elif [ $a -eq $b or $b -eq $c ] ; then
echo "ISOSCELES"
else
echo "SCALENE"
fi
I just want to know, what to use instead of and and or?
Use && for and (|| for or)
read a b c
if [ "$a" == "$b" ] && [ "$b" == "$c" ] ; then
echo "EQUILATERAL"
elif [ "$a" == "$b" ] || [ "$b" == "$c" ] ; then
echo "ISOSCELES"
else
echo "SCALENE"
fi
Use && and || to have multiple conditions. Additionally, change the square brackets to parentheses. Additionally change the -eq to == since you're comparing numbers and not strings. This works:
#!/bin/bash
read a b c
if (( $a == $b )) && (( $b == $c )); then
echo "EQUILATERAL"
elif (( $a == $b )) || (( $b == $c )) ; then
echo "ISOSCELES"
else
echo "SCALENE"
fi
In addition to the prior answers, the correct way to use compound expression in a single [ or test (they are the same) clause is to use -a (for and) and -o (for or).
(e.g. testing if both file1 and file2 are readable):
if [ -r "$file1" -a -r "$file2 ]
then
# do something with the files
fi
Using test itself:
if test -r "$file1" -a -r "$file2
then
# do something with the files
fi
The portable way of doing this inside test brackets is to use -a and -o. Beware however that -eq is a numeric comparison, so you need to make sure your variables are numeric before comparing them. Something like this:
#! /bin/sh
read a b c
expr "$a" : '[0-9][0-9]*$' \& "$b" : '[0-9][0-9]*$' \& "$c" : '[0-9][0-9]*$' >/dev/null || exit
if [ $a -eq $b -a $b -eq $c ] ; then
echo "EQUILATERAL"
elif [ $a -eq $b -o $b -eq $c ] ; then
echo "ISOSCELES"
else
echo "SCALENE"
fi

Error executing shell script

I am trying to execute the following shell script
#!/bin/sh
echo "start"
if [ $# != 2 || $1 != "first" || $1 != "second" ]
then
echo "Error"
fi
echo "done"
and I'm getting the following output:
start
./autobuild.sh: line 3: [: missing `]'
./autobuild.sh: line 3: !=: command not found
./autobuild.sh: line 3: !=: command not found
done
I have no idea how to resolve the errors. Even if I use -ne instead of !=, I get the same errors. Please help.
Your syntax is incorrect. If you want multiple conditions in an if statement you need to have multiple [] blocks. Try:
if [ $# != 2 ] || [ $1 != "first" ] || [ $1 != "second" ]
But, it's better to use [[ (if your shell supports it) as it is safer to use. I would go for:
if [[ $# -ne 2 || $1 != "first" || $1 != "second" ]]
See this question on brackets: Is [[ ]] preferable over [ ] in bash scripts?
While OR ing the conditions should be seperate as follows :
#!/bin/sh
echo "start"
if [ $# != 2] || [ $1 != "first" ] || [ $1 != "second" ]
then
echo "Error"
fi
echo "done"
Try substituting -NE for !=.
if-usage samples
This should work:
#!/bin/sh
echo "start"
if [ $# -ne 2 -o $1 -ne "first" -o $1 -ne "second" ]
then
echo "Error"
fi
echo "done"

Consolidate multiple if statements in Ksh

How can I consolidate the following if statements into a single line?
if [ $# -eq 4 ]
then
if [ "$4" = "PREV" ]
then
print "yes"
fi
fi
if [ $# -eq 3 ]
then
if [ "$3" = "PREV" ]
then
print "yes"
fi
fi
I am using ksh.
Why does this give an error?
if [ [ $# -eq 4 ] && [ "$4" = "PREV" ] ]
then
print "yes"
fi
Error:
0403-012 A test command parameter is not valid.
Try this:
if [[ $# -eq 4 && "$4" == "PREV" ]]
then
print "yes"
fi
You can also try putting them all together like this:
if [[ $# -eq 4 && "$4" == "PREV" || $# -eq 3 && "$3" == "PREV" ]]
then
print "yes"
fi
Do you just want to check if the last argument is "PREV"? If so, you can also do something like this:
for last; do true; done
if [ "$last" == "PREV" ]
then
print "yes"
fi
'[' is not a grouping token in sh. You can do:
if [ expr ] && [ expr ]; then ...
or
if cmd && cmd; then ...
or
if { cmd && cmd; }; then ...
You can also use parentheses, but the semantics is slightly different as the tests will run in a subshell.
if ( cmd && cmd; ); then ...
Also, note that "if cmd1; then cmd2; fi" is exactly the same as "cmd1 && cmd2", so you could write:
test $# = 4 && test $4 = PREV && echo yes
but if your intention is to check that the last argument is the string PREV, you might consider:
eval test \$$# = PREV && echo yes
Try this :
if [ $# -eq 4 ] && [ "$4" = "PREV" ]
then
print "yes"
fi

How to do a logical OR operation for integer comparison in shell scripting?

I am trying to do a simple condition check, but it doesn't seem to work.
If $# is equal to 0 or is greater than 1 then say hello.
I have tried the following syntax with no success:
if [ "$#" == 0 -o "$#" > 1 ] ; then
echo "hello"
fi
if [ "$#" == 0 ] || [ "$#" > 1 ] ; then
echo "hello"
fi
This should work:
#!/bin/bash
if [ "$#" -eq 0 ] || [ "$#" -gt 1 ] ; then
echo "hello"
fi
I'm not sure if this is different in other shells but if you wish to use <, >, you need to put them inside double parenthesis like so:
if (("$#" > 1))
...
This code works for me:
#!/bin/sh
argc=$#
echo $argc
if [ $argc -eq 0 -o $argc -eq 1 ]; then
echo "foo"
else
echo "bar"
fi
I don't think sh supports "==". Use "=" to compare strings and -eq to compare ints.
man test
for more details.
If you are using the bash exit code status $? as variable, it's better to do this:
if [ $? -eq 4 -o $? -eq 8 ] ; then
echo "..."
fi
Because if you do:
if [ $? -eq 4 ] || [ $? -eq 8 ] ; then
The left part of the OR alters the $? variable, so the right part of the OR doesn't have the original $? value.
Sometimes you need to use double brackets, otherwise you get an error like too many arguments
if [[ $OUTMERGE == *"fatal"* ]] || [[ $OUTMERGE == *"Aborting"* ]]
then
fi
If a bash script
If [[ $input -gt number || $input -lt number ]]
then
echo .........
else
echo .........
fi
exit
have you tried something like this:
if [ $# -eq 0 ] || [ $# -gt 1 ]
then
echo "$#"
fi
From Bash Reference Manual → 3.4.2 Special Parameters
#
($#) Expands to the number of positional parameters in decimal.
Therefore, $# will always be either 0 or a bigger integer.
So if you want to do something whenever $# is either 0 or bigger than 1, you just have to check if $# is or is not 1:
[ $# -eq 1 ] && echo "1 positional param" || echo "0 or more than 1"
This uses the syntax:
[ condition ] && {things if true} || {things if false}
And in Bash
line1=`tail -3 /opt/Scripts/wowzaDataSync.log | grep "AmazonHttpClient" | head -1`
vpid=`ps -ef| grep wowzaDataSync | grep -v grep | awk '{print $2}'`
echo "-------->"${line1}
if [ -z $line1 ] && [ ! -z $vpid ]
then
echo `date --date "NOW" +%Y-%m-%d` `date --date "NOW" +%H:%M:%S` ::
"Process Is Working Fine"
else
echo `date --date "NOW" +%Y-%m-%d` `date --date "NOW" +%H:%M:%S` ::
"Prcess Hanging Due To Exception With PID :"${pid}
fi
OR in Bash
line1=`tail -3 /opt/Scripts/wowzaDataSync.log | grep "AmazonHttpClient" | head -1`
vpid=`ps -ef| grep wowzaDataSync | grep -v grep | awk '{print $2}'`
echo "-------->"${line1}
if [ -z $line1 ] || [ ! -z $vpid ]
then
echo `date --date "NOW" +%Y-%m-%d` `date --date "NOW" +%H:%M:%S` ::
"Process Is Working Fine"
else
echo `date --date "NOW" +%Y-%m-%d` `date --date "NOW" +%H:%M:%S` ::
"Prcess Hanging Due To Exception With PID :"${pid}
fi

Resources