Bad Substitution when I try to print a specific position of array [duplicate] - bash

This question already has answers here:
Difference between sh and Bash
(11 answers)
Closed 10 months ago.
I'm getting started with bash programming, and I want to print a specific position of array, but when I try I get this error: Bad substitution
#!/bin/sh
user=`cut -d ";" -f1 $ultimocsv | sort -d | uniq -c`
arr=$(echo $user | tr " " "\n")
a=5
echo "${arr[$a]}" #Error:bad substitution
why?

You are using "sh" which does not support arrays. Even if you would use the "bash" you get the same error, because the "arr" will not be an array. I am not sure, if the "-c" at "uniq" is what you wanted.
I assume, this is what you are looking for:
#!/bin/bash
mapfile -t arr < <( cut -d ";" -f1 $ultimocsv | sort -d | uniq )
a=5
echo "${arr[$a]}"
This will not give the error, even if your file has less than 5 unique lines, because bash will return an empty string for a defined but empty array.
It works even with "uniq -c", because it puts complete lines in the array.

Related

How to pass string variable in cut shell command [duplicate]

This question already has answers here:
How to pass the value of a variable to the standard input of a command?
(9 answers)
Closed 1 year ago.
Assume that I have :
.sh file having these commands :
#!/bin/bash
GIT_BRANCH="origin/release/2.4.0"
echo $GIT_BRANCH
then, I want to compute new varible from the GIT_BRANCH (operation of substring) :
So,
RELEASE_VERSION=$( $GIT_BRANCH | cut -d "/" -f3)
echo $RELEASE_VERSION
But this does return message error : bad substitution
I tried many possibilities in the RELEASE_VERSION, but no result.
like
RELEASE_VERSION=$(echo $GIT_BRANCH | cut -d "/" -f3)
RELEASE_VERSION=$("$GIT_BRANCH" | cut -d "/" -f3) and this return empty results
You are definitelly missing an echo statement. Following code works for me just fine.
GIT_BRANCH="origin/release/2.4.0"
RELEASE_VERSION=$(echo $GIT_BRANCH | cut -d "/" -f3)
echo $RELEASE_VERSION

bash script pipe with several commands [duplicate]

This question already has an answer here:
Bash - Unexpected End of File [closed]
(1 answer)
Closed 4 years ago.
I have next simple script
#!/bin/bash
shopt -s lastpipe
echo "hello" | { read test1; hashID=$(echo -n "$test1" | md5sum | cut -d" " -f1) }
when I do run this script bash returns: syntax error: unexpected end of file. Where did I wrong?
as #Cyrus said, it works
echo "hello" | { read test1; hashID=$(echo -n "$test1" | md5sum | cut -d" " -f1); }
Thanks #Cyrus

Assigning a command output to a shell script variable [duplicate]

This question already has answers here:
How do I set a variable to the output of a command in Bash?
(15 answers)
Closed 2 years ago.
How do I assign a command output to a shell script variable.
echo ${b%?} | rev | cut -d'/' -f 1 | rev
${b%?} gives me a path..for example: /home/home1
The above command gives me home1 as the output. I need to assign this output to a shell script variable.
I tried the below code
c=${b%?} |rev | cut -d '/' -f 1 | rev
echo $c
But it didn't work.
To assign output of some command to a variable you need to use command substitution :
variable=$(command)
For your case:
c=$(echo {b%?} |rev | cut -d '/' -f 1 | rev)
Just wondering why dont you try
basename ${b}
Or just
echo ${b##*/}
home1
If you want to trim last number from your path than:
b="/home/home1"
echo $b
/home/home1
b=${b//[[:digit:]]/}
c=$(echo ${b##*/})
echo ${c}
home
Just like this:
variable=`command`

Counting words and characters in Bash without wc [duplicate]

This question already has answers here:
Length of string in bash
(11 answers)
Closed 2 years ago.
I have a variable set like this:
sentence="a very long sentence with multiple spaces"
I need to count how many words and characters are there without using other programs such as wc.
I know counting words can be done like this:
words=( $sentence )
echo ${#words[#]}
But how do I count the characters including spaces?
But how do I count the characters including spaces?
To count length of string use:
echo "${#sentence}"
47
You can also use grep with a regex that matches everything:
echo "this string" | grep -oP . | grep -c .
Using awk on a single line:
echo this string | awk '{print length}'
Another way of piping stdin text to awk:
awk '{print length}' <<< "this string"

How to process values from for loop in shell script

I have below for loop in shell script
#!/bin/bash
#Get the year
curr_year=$(date +"%Y")
FILE_NAME=/test/codebase/wt.properties
key=wt.cache.master.slaveHosts=
prop_value=""
getproperty(){
prop_key=$1
prop_value=`cat ${FILE_NAME} | grep ${prop_key} | cut -d'=' -f2`
}
#echo ${prop_value}
getproperty ${key}
#echo "Key = ${key}; Value="${prop_value}
arr=( $prop_value )
for i in "${arr[#]}"; do
echo $i | head -n1 | cut -d "." -f1
done
The output I am getting is as below.
test1
test2
test3
I want to process the test2 from above results to below script in place of 'ABCD'
grep test12345 /home/ptc/storage/**'ABCD'**/apache/$curr_year/logs/access.log* | grep GET > /tmp/test.access.txt
I tried all the options but could not able to succeed as I am new to shell scripting.
Ignoring the many bugs elsewhere and focusing on the one piece of code you say you want to change:
for i in "${arr[#]}"; do
val=$(echo "$i" | head -n1 | cut -d "." -f1)
grep test12345 /dev/null "/home/ptc/storage/$val/apache/$curr_year/logs/access.log"* \
| grep GET
done > /tmp/test.access.txt
Notes:
Always quote your expansions. "$i", "/path/with/$val/"*, etc. (The * should not be quoted on the assumption that you want it to be expanded).
for i in $prop_value would have the exact same (buggy) behavior; using arr buys you nothing. If you want using arr to increase correctness, populate it correctly: read -r -a arr <<<"$prop_value"
The redirection is moved outside the loop -- that way the second iteration through the loop doesn't overwrite the file written by the first one.
The extra /dev/null passed to grep ensures that its behavior is consistent regardless of the number of matches; otherwise, it would display filenames only if more than one matching log file existed, and not otherwise.

Resources