bash variable expansion in for loop sub-command [duplicate] - bash

This question already has answers here:
How do I use variables in single quoted strings?
(8 answers)
Closed 4 years ago.
Trying to expand a for loop variable in this does not succeed -
I am trying to use the $i variable in the jsonpath for loop below:
for i in {0..9}; do
echo $i
kubectl exec -i -t "$(kubectl get pod -l "app=mdm-shard" -o jsonpath='{.items[{$i}].metadata.name}')" -- cat /proc/net/udp
done
I get:
0
error: error parsing jsonpath {.items[{$i}].metadata.name}, invalid array index {$i}
error: pod name must be specified
I tried a lot of combinations but can't find the one that is going to expand $i inside the query.
My bash version:
GNU bash, version 4.4.19(1)-release (x86_64-pc-linux-gnu)

Thank you Benjamin - yes this worked:
for i in {0..9}; do
echo $i
kubectl exec -i -t "$(kubectl get pod -l "app=mdm-shard" -o jsonpath="{.items[$i].metadata.name}")" -- cat /proc/net/udp;
done

Related

Prevent bash adding single quotes [duplicate]

This question already has answers here:
Reading quoted/escaped arguments correctly from a string
(4 answers)
Convert a string into an array with bash, honoring quotes for grouping [duplicate]
(3 answers)
Bash doesn't parse quotes when converting a string to arguments
(5 answers)
Closed last year.
I am trying to execute a command like this
./build -t -c cflag="-Os -march=haswell"
The following is my script:
#!/bin/bash
set -x
ARGS=" -t"
MARCH=${MARCH:-haswell}
CFLAG="-Os"
CFLAG+=" -march=$MARCH"
ARGS+=" -c cflag=\"${CFLAG}\""
./build $ARGS
Here is build:
#!/usr/bin/env python3
import sys
for arg in sys.argv:
print(arg)
Bash always adding extra single quotes in the command:
+ ARGS=' -t'
+ MARCH=haswell
+ CFLAG=-Os
+ CFLAG+=' -march=haswell'
+ ARGS+=' -c cflag="-Os -march=haswell"'
+ ./build -t -c 'cflag="-Os' '-march=haswell"'
./build
-t
-c
cflag="-Os
-march=haswell"
Is there a way to disable this behavior in bash?

getting variable name in file name for bash [duplicate]

This question already has answers here:
When do we need curly braces around shell variables?
(7 answers)
Closed 4 years ago.
I wanted to change the name of my file from file.txt to file_4i.txt and file_5i.txt according to the number I need but when I use the command below, the file name changes to file_.txt and the value of m never is indicated. I wanted to get 4i but $mi does not work either.
sudo sh -c "m=4 ; mv file.txt file_$mi.txt"
sudo sh -c "m=4 ; mv file.txt file_$m.txt"
Use single quotes so the variable doesn't expand early, and use {} so mi isn't interpreted as the variable name:
sudo sh -c 'm=4 ; mv file.txt file_${m}i.txt'
sudo sh -c 'm=4 ; mv file.txt file_$m.txt'

Bash while stops at first iteration [duplicate]

This question already has answers here:
Capturing output of find . -print0 into a bash array
(13 answers)
Closed 7 years ago.
I am currently a bash script that shall check some data. What I got so far is:
!/bin/bash
#!/bin/bash
find "./" -mindepth 1 -maxdepth 1 -type d -print0 | while IFS= read -r -d '' file; do
folder=${file##*/}
echo "Checking ${folder} for sanity..."
./makeconfig ${folder} | while read -r line; do
title=`echo $line | awk -F' ' '{print $2}'`
echo $title
done
done
Now what it currently does is: Search every directory in ./ and extract the folders name (thus: removing the ./ from the result of find). Then give it to a self-written tool, which will output some lines like this:
-t 1 -a 2
-t 3 -a 5
-t 7 -a 7
-t 9 -a 8
of which I gather the value behind -t via awk. This also works so far, the problem is, the outer while loop stops after the first iteration, thus checking only one folder. My guess is that the two read commands of the inner and outer loop are colliding somehow. The tool makeconfig definitiveley returns 0 (no error) always. I tried to debug it using sh -x script.sh but it does not show me anything I can deal with.
Can someone point me in the right direction here what is going wrong? If you need ANY further informations, I can give them to you. Ive written a quick mimicking program if you want to test the bash script here (also a script now, just echoing some stuff), just make it executable via chmod +x:
echo "-t 3 -a 4"
echo "-t 6 -a 1"
echo "-t 9 -a 5"
Just put this with the script in a folder and create some subfolders, that should do it to make it work (as much as it does).
Thanks in advance!
EDIT: This is NOT a duplicate as mentioned. The problem here are more the nested read commands than the print0 (maybe that has also something to do with it, but not entirely).
IFS= isn't setting the field separator to the null string (\0), but unsetting it entirely, so the entire output of the find command is being read at once. If you run it without the -print0 argument to find it'll be easier to work with in bash. Two other alternatives:
use xargs to run a shell script on each item found with that being the sole argument
use -exec to run the shell script on each item.

Unexpected '(' in bash [duplicate]

This question already has answers here:
Bash: Syntax error: redirection unexpected
(9 answers)
Closed 8 years ago.
I have the following script:
#!/bin/sh
# Use the PhiPack software on our two aligned sets of sequences...
mkdir FcFeABC
cd FcFeABC
../bin/PhiPack/Phi -f ../../Data/Real_Sequences_and_Networks/FcFeABC_alignment.fas -o -v -w 10 -g
cd -
mkdir FcL10
cd FcL10
../bin/PhiPack/Phi -f ../../Data/Real_Sequences_and_Networks/FcL10_alignment.fas -o -v -w 10 -g
cd -
# Use the PhiPack software on the simulated Datasets...
cd ../Data/Simulated_Sequences_and_Networks/Constant_Sex/Theta\ =\ 0.066/Theta\ =\ 0.066/Medium/CutSequences/;
rmus=($(ls -d *.fas))
cd -
absfiles=(../Data/Simulated_Sequences_and_Networks/Constant_Sex/Theta\ =\ 0.066/Theta\ =\ 0.066/Medium/CutSequences/*.fas)
if [ ${#rmus[#]} = ${#absfiles[#]} ]
then
mkdir ${rmus[#]}
for ((i=0; i<${#absfiles[#]}; i++));
do
cd ${rmus[$i]}
.../bin/PhiPack/Phi -f ${absfiles[$i]} -o -v -w 10 -g
cd -
done
else
echo "Error, Number of files created and files to be read differs"
fi
Which hit's an error at line 16:
./runPhiTests.sh: 16: ./runPhiTests.sh: Syntax error: "(" unexpected
Which is this line:
rmus=($(ls -d *.fas))
I don't understand why the '(' is unexpected - it's a simple assignment of the results of ls to an array.
Thanks,
Ben W.
You aren't running it with bash. You are running with /bin/sh from your shebang line #!/bin/sh.
Either run with bash explicitly bash runPhiTests.sh or fix your shebang line #!/bin/bash.
Try to use #!/bin/bash instead of sh.

Unable to store python --version to a shell variable [duplicate]

This question already has answers here:
How to append output of "python --version" to a file in bash shell?
(2 answers)
Closed 8 years ago.
I need to get the version of Python installed and store it in a variable for later use. Whereas it is printing on the console instead of storing to variable. I am able to store output of ls command in a variable. Please check the below code :
root#myhost:/volumes/srini# cat python_version.sh
python_version=`python --version`
echo "\****"
echo $python_verison
echo "\****"
ls_output=`ls -l python*`
echo "\****"
echo $ls_output
echo "\****"
Please check the output of the code :
root#myhost:/volumes/srini# ./python_version.sh
Python 2.6.8
\****
\****
\****
-rwxr-xr-x 1 root root 147 May 26 09:35 python_version.sh
\****
Seems like that value gets sent to stderr for some reason, as in this question.
I find that the following seems to work:
python_version=$(python --version 2>&1)
echo "\****"
echo $python_version
echo "\****"
gives
\****
Python 2.7.3
\****
The value of python_version is set locally when the script is run. It has no impact on the invoking shell. If you want that variable to be set in the current shell, you can accomplish that using one of the following methods.
Run the following command in your current shell.
python_version=$(python --version 2>&1)
Create a file that contains the above line. Say that file is python_version.sh. Then execute:
source python_vesion.sh

Resources