BASH - Get number from a file and use it - bash

I have a test.txt file that looks like this:
flask=1.0.1
control=1.0.1
device=1.0.1
Now, I want to create an if statement that if flask=1.0.1, do something and if flash=1.0.1_hotfix do something else.
I tried with grep -iFq but no luck, I am newbie to bash and also to programming.
Can anyone show me a doc that explains how to do so? It's really simple task.
Thank you all!

With bash and if:
source test.txt
if [[ $flask == 1.0.1 ]]; then
echo "do something"
fi
if [[ $flask == 1.0.1_hotfix ]]; then
echo "do something else"
fi
Or with bash and case:
source test.txt
case $flask in
1.0.1)
echo "do something"
;;
1.0.1_hotfix)
echo "do something else"
;;
esac
Or in a denser presentation:
source test.txt
case $flask in
1.0.1) echo "do something" ;;
1.0.1_hotfix) echo "do something else" ;;
esac

Grep is fine, just notice that flask=1.0.1 is a substring of flask=1.0.1_hotfix, so you need to do full string comparison or check for the string end.
flask=$( grep ^flask= test.txt )
if [ "$flask" == flask=1.0.1 ] ; then
...
elif [ "$flask" == flask=1.0.1_hotfix ] ; then
....
fi

I've understood you correctly?
[root#212-24-57-104 Build]# cat 1
flask=1.0.1
control=1.0.1
device=1.0.1
[root#212-24-57-104 Build]# cat ez.sh
#!/bin/bash
a=( $(cat 1) )
for ver in "${a[#]}"
do
if [ $(echo "${ver}" | awk -F= '{print $NF}') == "1.0.1" ]
then
echo "Do something virh $ver"
else
echo "Do anything else with $ver"
fi
done

A couple of other options:
use grep to get the value
flask_value=$( grep -oP '^flask=\K.*' test.txt )
case $flask_value in
1.0.1) ... ;;
# etc
esac
iterate over the file with just bash:
while IFS="=" read var value; do
if [[ $var == "flask" ]]; then
case $value in
1.0.1) ... ;;
# etc
esac
fi
done < test.txt

Related

How to display only once echo command in a Bash loop

My problem is pretty simple. I have :
a=$(echo "lol")
for i in {1..3};
do
echo $a && echo $i ;
done
I get :
lol
1
lol
2
lol
3
I would like to print only once the variable a at the beginning of the output , to get :
lol
1
2
3
Any idea?
You don't need a loop at all
a=$(echo "lol") # Not sure why poster wrote this rater than a=lol
printf %s\\n "$a" {1..3}
I suggest:
#!/bin/bash
a="lol"$'\n' # append newline
for i in {1..3}
do
echo -e "$a$i" # -e: enable interpretation of escape sequences
unset a
done
Or replace in your question
echo $a && echo $i ;
with
[[ "$i" == "1" ]] && echo "$a"
echo "$i"
See: help echo and help unset
Move the echo outside of the for loop
a=$(echo "lol")
echo $a
for i in {1..3}; do
echo $i;
done
or:
echo "lol"
for i in {1..3}; do
echo $i;
done
test run in shell

Shell variable value passing to subshell?

I am writing script in shell and it's something like:
temp=0
while true; do
case "a" in
a) temp=5; ;;
esac
break
done | echo "$temp"
( temp value is condition for if in subshell and | (pipe) is needed as stdout redirect to stdin)
and I need in temp 5 but I got 0 in echo. Any way to preserve value inside case (posixly correct without tempfile)?
Do you want it like this? Prints 5 and 0.
#!/bin/sh
temp=0
while true; do
case "a" in
a) temp=5; echo "$temp" ;;
esac
break
done | cat
echo "temp unchanged because of subshell $temp"
Would this help you, filtering out your status?
I still don't get why you need a pipe and how you expect the other command you pipe into to react on a status. It's just not the way it works. You evaluate conditions in your script and call commands accordingly.
#!/bin/sh
filter(){
data=''
while read line; do
case "$line" in
temp=5) temp=5 ;;
*) data=$(printf '%s\n' "$data"; printf '%s\n' "$line") ;;
esac
done
if [ "$temp" -eq 5 ]; then
echo "do this 5 with data"
else
echo "do that other with data"
echo "$data"
fi
}
temp=0
while true; do
case "a" in
a) temp=5; printf 'temp=%s\n' "$temp"; for i in $(seq 1 30); do echo "30 lines"; done ;;
esac
break
done | filter
echo "temp unchanged because of subshell $temp"

How to use if inside a command in bash script?

I am writing a script in bash, and I have a problem with it:
select opt in "${options[#]}"
do
case $opt in
"1) Check Cassandra Status.")
ssh skyusr#"$IP" "export JAVA_HOME=/opt/mesosphere && /var/lib/mesos/slave/slaves/*/frameworks/*/executors/*/runs/latest/apache-cassandra-3.0.10/bin/nodetool -p 7199 status" | sed -n '6,10p' | awk '{print $1,$2}' | DN="$(grep DN)" | [[if [[!DN]]; echo "All Good" else "Node(s) "$DN" is Down" ;fi]]
;;
"2) Run Repair on all nodes.")
echo "you chose choice 2"
;;
"3) Run Refresh on specific keyspace/Table.")
echo "you chose choice 3"
;;
"4) Optional")
echo "This option disabled"
;;
"Quit")
break
;;
*) echo invalid option;;
esac
done
It gives me
error:line 16: [[if: command not found
All was working until I added this if command, I need to echo a message if $DN is empty else echo another message .
You seem to be confused about some of Bash's basic concepts like pipelines (|) versus compound commands (if and [[). For example awk '{print $1,$2}' | DN="$(grep DN)" does probably not do what you expect:
$ echo $'a\nb'
a
b
$ echo $'a\nb' | B=$(grep a)
$ echo $B
Note how the variable B is not set to "a".
Furthermore your syntax DN="$(grep DN)" | [[if [[!DN]]; echo "All Good" is complete nonsense. You best start by reading some introduction. Then you can continue along the lines of:
A=$(....)
[[ -z $A ]] && echo "A is empty"
# or
if [[ -z $A ]] then echo "A is empty"; else echo "A is not empty"; fi
Change your if condition like below. Your if condition syntax is not correct and then part is also missing. I have just corrected the if condition rest you need to check again.
if [[ DN == "" ]]; then echo "All Good" else echo "Node(s) $DN is Down" ; fi

shell script: "'<<' unmatched"-syntax error using here document

Hi I am attempting to write a program that will alert the user if a person of interest has come online at a given time. My program thus far is
#!/usr/bin/ksh
message=""
when=""
validFiles=""
validUsers=""
if [ $# -gt 0 ] ; then
while getopts w:m: opt
do
case $opt in
w) when=$OPTARG;;
m) message=$OPTARG;;
\?) echo $USAGE exit 2;;
esac
done
shift $(($OPTIND - 1))
if [[ $# -gt 0 ]] ; then
for i; do
if [[ -f "$i" && -r "$i" ]]; then
if ! echo $validFiles | grep $i >/dev/null; then
validFiles="$validFiles $i"
fi
elif id $i 2> /dev/null 1>&2; then
if ! echo $validUsers | grep $i > /dev/null; then
validUsers="$validUsers $i"
fi
fi
done
if [[ $when != "" && $validFiles != "" || $validUsers != "" ]] ;then
for i in $validUsers; do
if ! grep $i $validFiles >/dev/null; then
at $when <<"END"
if finger $i | grep $i; then
echo "$i is online" | elm $message
fi
END
fi
done
fi
else
echo "No files or usernames"
fi
else
echo "No arguments provided"
fi
My problem is that when I attempt to run this I get the error message
syntax error at line 33 : `<<' unmatched
I am not sure as to why this is appearing. I have checked many other examples and my at command,here document, appears to be the same as theirs. Could anybody help me out? Thanks.
The here string delimiter must not be indented, your END should be at the beginning of the line:
$ cat <<EOT
> foo
> bar
> EOT
foo
bar
If you want the trailing delimiter to be indented you can use the following syntax, but this will also strip all leading tabs from the here document itself (this only works with tabs!):
$ cat <<-EOT
> foo
> bar
> quux
> EOT
foo
bar
quux
Note that this behaviour is specified by POSIX so should work in all compliant shells:
If the redirection symbol is "<<-", all leading tabs shall be stripped from input lines and the line containing the trailing delimiter.

filename match based on a known file name

I want a user to input the filename which could be reside at any location but the name of the file is fixed in end .i.e. abc. txt
Let suppose the the user inputs the file name as /usr/test/abc.txt which comes in second positional parameter in my script
I want to make below statement as true how can I achieve this
if [ $2 == ..../abc.txt ]
Thanks,
Ruchir
Let suppose the the user inputs the file name as /usr/test/abc.txt which comes in second positional parameter in my script
I want to make below statement as true how can I achieve this
Use this if condition using shell glob:
if [[ "/$2" == *"/abc.txt" ]]; then
echo "valid match"
fi
You can use basename to get the last component of the filename.
prompt> cat foo.sh
#!/bin/sh
if [ "abc.txt" == `basename $2` ]; then
echo "found .../abc.txt"
fi
prompt> foo.sh foo /a/b/c/abc.txt
found .../abc/txt
you could do:
if ( echo "$2" | grep 'abc.txt$' >/dev/null ) ; then ... ; else .... ; fi
or
if ( echo "$2" | grep '/abc.txt$' >/dev/null ) ; then ... ; else .... ; fi
(if you need that "/" too ?)
if [[ $2 == *"/abc.txt" ]]; then
echo "It ends with abc.txt";
fi
Why [[ ]] works compared to [ ] is explained here...
"[ ]" vs. "[[ ]]" in Bash shell

Resources