Home > Blockchain >  Why are quotes preserved when using bash $() syntax, but not if executed manually?
Why are quotes preserved when using bash $() syntax, but not if executed manually?

Time:01-19

I have the following bash script:

$ echo $(dotnet run --project Updater)
UPDATE_NEEDED='0' MD5_SUM="7e3ad68397421276a205ac5810063e0a"

$ export UPDATE_NEEDED='0' MD5_SUM="7e3ad68397421276a205ac5810063e0a"

$ echo $UPDATE_NEEDED
0

$ export $(dotnet run --project Updater)

$ echo $UPDATE_NEEDED
'0'

Why is it $UPDATE_NEEDED is 0 on the 3rd command, but '0' on the 5th command?

What would I need to do to get it to simply set 0? Using UPDATE_NEEDED=0 instead is not an option, as some of the other variables may contain a space (And I'd like to optimistically quote them to have it properly parse spaces).

Also, this is a bit of a XY problem. If anyone knows an easier way to export multiple variables from an executable that can be used later on in the bash script, that could also be useful.

CodePudding user response:

To expand on the answer by Glenn:

  1. When you write something like export UPDATE_NEEDED='0' in Bash code, this is 100% identical to export UPDATE_NEEDED=0. The quotes are used by Bash to parse the command expression, but they are then discarded immediately. Their only purpose is to prevent word splitting and to avoid having to escape special characters. In the same vein, the code fragment 'foo bar' is exactly identical to foo\ bar as far as Bash is concerned: both lead to space being treated as literal rather than as a word splitter.

  2. Conversely, parameter expansion follows different rules, and preserves literal quotes.

  3. When you use eval, the command line arguments passed to eval are treated as if they were Bash code, and thus follow the same rules of expansion as regular Bash code, which leads to the same result as (1).

CodePudding user response:

Apparently that Updater project is doing the equivalent of

echo "UPDATE_NEEDED=\'0\' MD5_SUM=\"7e3ad68397421276a205ac5810063e0a\""

It's explicitly outputting the quotes.

When you do export UPDATE_NEEDED='0' MD5_SUM="7e3ad68397421276a205ac5810063e0a", bash will eventually remove the quotes before actually setting the variables.

I agree with @pynexj, eval is warranted here, although additional quoting is recommended:

eval export "$(dotnet ...)"
  •  Tags:  
  • Related