muilpp
muilpp

Reputation: 1353

Quadruple nested quotations in bash script

I'm using curl to get items from a GraphQL API. I need to send the item name to get the id of it as a response. This works fine when the name is just one word, but I can't seem to make it work when it contains blank spaces.

itemName="Variable with blank spaces"
curl -X POST -data '{"query": "{getItems(jql: \"text ~ '$itemName'\") {results {id}}"}'

How can I escape the $itemName in the query above

Upvotes: 0

Views: 165

Answers (2)

Ed Morton
Ed Morton

Reputation: 204558

You can't include a ' in a '-delimited string or script in any shell. No amount of attempted escaping will make it work. Period. So to get a ' to appear in a command-line you need to break out of the enclosing 's, provide a ', then get back into it to continue with the rest of the '-delimited string/command.

The usual syntax to get a ' into a string is to use '\'' wherever a ' is needed, eg.:

str='foo'\''bar'

sets the variable str to foo'bar.

So, with your command line you'd use the following to get 's:

curl -X POST -data '{"query": "{getItems(jql: \"text ~ '\''$itemName'\''\") {results {id}}"}'

but you additionally need to let the shell expand $itemName which you ALSO need to break out of the 's for and also double-quote while back in the shell to avoid globbing and expansion (see https://mywiki.wooledge.org/Quotes). You could write that as:

curl -X POST -data '{"query": "{getItems(jql: \"text ~ '\'''"$itemName"''\''\") {results {id}}"}'

but we're getting a '-pileup getting immediately in/out of the shell twice there that's not necessary - just stay in shell and expand the variable while you're there. So you can reduce it to:

curl -X POST -data '{"query": "{getItems(jql: \"text ~ '\'"$itemName"\''\") {results {id}}"}'

or, since \' is the same as "'":

curl -X POST -data '{"query": "{getItems(jql: \"text ~ '"'$itemName'"'\") {results {id}}"}'

Upvotes: 1

KamilCuk
KamilCuk

Reputation: 141890

You have to escape the '. So end quoting ' escape single \' then add the item "$itemName" then add single quote \' and re-start single quoting '.

curl -X POST -data '{"query": "{getItems(jql: \"text ~ '\'"$itemName"\''\") {results {id}}"}'

or use ":

curl -X POST -data "{\"query\": \"{getItems(jql: \\\"text ~ '$itemName'\\\") {results {id}}\"}"

Upvotes: 1

Related Questions