1

I am reading in a file inside my bash script where each line consists of multiple columns like this:

ANSIBLE 'first run' '--diff --extra-vars "client=yes fast=no"'

As you can see, the line consists of three columns, the ones with whitespaces in apostrophes. The third column contain options for a binary to call. As I read in the file, I stored those options to a variable:

custom_options=${columns[2]}

This evaluates to

custom_options='--diff --extra-vars "client=yes fast=no"'

Now I want to execute my binary with those options:

ansible-playbook $custom_options site.yml

However this fails, because on execution there were added apostrophes around the inner string:

ansible-playbook --diff --extra-vars '"client=yes fast=no"' site.yml

Does anybody know how to substitute the variable string as-is?

Here is a short script to quickly reproduce the behavior:

#!/bin/bash
set -x
touch "as is"
command='-name "as is"'
find . $command -type f
3

1 Answer 1

2

I found a workaround rather than a solution. I surrounded the whole command with the variable inside an eval expression:

eval "ansible-playbook $custom_options site.yml"

Here the equivalent usage within the example script:

...
eval "find . $command -type f"

I am no bash guru and I don't know if this workaround has any side effects. Nevertheless I tested following:

  • eval works with pipes: eval "command | tee file"
  • quotes inside eval are possible: eval "command \"${var}\""

However it fit my needs but it feels dirty. Better solutions are welcome.

2
  • That's the (well, a) right solution. It does mean you need to be very careful about what you put in the custom_options variable. Commented Mar 3, 2016 at 23:37
  • Of course @Gilles custom_options should be parsed for valid content before usage, to avoid injection points for malicious code. Good hint. Commented Mar 4, 2016 at 17:08

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .