5

I am trying to write a sed command to replace tokens in a file with values from environment variables like so:

export my_var=foo
echo 'something {{my_var}} bar' | sed -r "s/\{\{(.*?)\}\}/$\1/g"

I want to grab the name of the token (my_var in this case) and then substitute in the value of the environment variable with the same name.

Is this possible? Current the above prints something $my_var bar rather than something foo bar which is what I want.

I'm open to using another tool such awk instead if it's not possible with sed.

toby
  • 683
  • 2
  • 6
  • 16

2 Answers2

4

After you replace {{my_var}} with $my_var, you need to send the string for a second round of substitution explicitly.

with eval

$ eval echo "$(echo 'something {{my_var}} bar' | sed 's/{{\([^}]\+\)}}/$\1/g')"
something foo bar

or with a subshell

$ echo 'echo something {{my_var}} bar' | sed 's/{{\([^}]\+\)}}/$\1/g' | sh
something foo bar

Perl can do this 2nd round of evaluation on the replacement text only, not the whole output (with the s/// function's e modifier):

$ echo 'something {{my_var}} bar' | perl -pe 's/\{\{(\w+)\}\}/$ENV{$1}/eg' 
something foo bar
glenn jackman
  • 238,783
  • 38
  • 220
  • 352
  • Thanks, the Perl example is exactly what i was looking for – toby Oct 09 '15 at 15:12
  • I also found [envsubst](https://www.gnu.org/software/gettext/manual/html_node/envsubst-Invocation.html), it uses a slightly different token format in the input but has the required functionality – toby Nov 24 '15 at 13:39
0

if you want to use variable then add $ sign before variable.

export my_var=foo

echo "something {{$my_var}} bar" | sed -r "s/{{(.*?)}}/$\1/g" | sed 's|[$]||g'

output:

something foo bar

Nullpointer
  • 1,895
  • 20
  • 26
  • Getting closer, that gives me `something $foo bar` any ideas how to drop the $ in the resulting string? The format in the original string can be whatever makes it easiest – toby Oct 09 '15 at 12:48
  • 1
    Thanks v much, that does work but i realise that there is an issue with my original example - $my_var is being substituted by the echo command rather than by sed so `echo 'something {{$my_var}} bar' | sed -r "s/\{\{(.*?)\}\}/$\1/g"` results in `something $$my_var bar` and `echo 'something {{$my_var}} bar' | sed -r "s/\{\{(.*?)\}\}/$\1/g" | sed 's|[$]||g'` results in `something my_var bar` – toby Oct 09 '15 at 13:07
  • @toby: Please update your question with exactly what you are looking for. – dawg Oct 09 '15 at 13:14