I have this bash script that lists all the jobs on jenkins. I have jobs with spaces within them and some without.
#!/bin/bash
for job in $(java -jar jenkins-cli.jar -s $JENKINS_URL -auth admin:admin list-jobs)
do
file_name="$(echo "$job" | sed 's/ /-/g').xml"
echo $file_name
java -jar jenkins-cli.jar -s $JENKINS_URL get-job $job > $file_name
done
I have jobs called for example:
- new job
- test-job
When I run this script however I get the following result:
new.xml
job.xml
test-job.xml
Instead I would like to output:
new-job.xml
test-job.xml
What am I missing here?
CodePudding user response:
Bash for loops splits when they see any whitespace like space, tab, or newline. So, you should use IFS (Internal Field Separator)
If lines end with "\n", try adding IFS=$'\n'
before the loop (you can use unset IFS
to reset it later)
You have a lot of examples here: How do I split a string on a delimiter in Bash?
CodePudding user response:
Space is also assigned to IFS by default and is respected during word splitting.
There are three common solutions here: First is to set IFS to $'\n'
temporily, as already suggested by Atxulo. Second is to use a while read
loop against a process substitution instance, which is useful for large or indefinite inputs. Third is to use readarray
which stores all input to an array. This one I believe being most practical to your problem.
readarray -t jobs < <(java ...)
for job in "${jobs[@]}"; do
Your script also has other issues. First is unnecessary use of sed. Just use ${param//pat/rep}
. You also allow multiple variables to undergo word splitting unnecessarily. Quote them.
Read the Bash manual for details.