I am trying to replace localhost in the string

$amp_conf['AMPDBHOST'] = 'localhost';

with the content of the variable {{ asterisk_db_host }}, which is

Even though

- replace:
    dest: /usr/src/freepbx/installlib/installcommand.class.php
    regexp: '(\$amp_conf\[.AMPDBHOST.\] = .)localhost(.;)'
    replace: '\1\2'

perfectly results in

$amp_conf['AMPDBHOST'] = 'localhost';

- replace:
    dest: /usr/src/freepbx/installlib/installcommand.class.php
    regexp: '(\$amp_conf\[.AMPDBHOST.\] = .)localhost(.;)'
    replace: '\1{{ asterisk_db_host }}\2'

as well as

- replace:
    dest: /usr/src/freepbx/installlib/installcommand.class.php
    regexp: '(\$amp_conf\[.AMPDBHOST.\] = .)localhost(.;)'
    replace: '\1{{ asterisk_db_host|regex_escape() }}\2'

replace the string with O2.17.0.2'; or O2\.17\.0\.2';.

What am I doing wrong here? How can I properly do this replacement?


Your replacement string looks like this:

'\1{{ asterisk_db_host }}\2'

After Jinja templating, this is what actually gets used as the replacement string in the regex module:


Look at that first term. It's no longer \1, it's now \1172, which is clearly erroneous. One way of solving this is to make the quotes around the value part of your replacement (because when you do this, there will be a non-digit character -- the quote -- separating your backreference from the value of the template expansion). Here's one option:

- hosts: localhost
  gather_facts: false
    asterisk_db_host: ""
    - replace:
        dest: ./cfgfile
        regexp: >-
          (\$amp_conf\[.AMPDBHOST.\] = )'localhost'(;)
        replace: >-
          \1'{{ asterisk_db_host }}'\2

This uses YAML block quoting (>-) so that we don't need to worry about escaping quotes in our expressions, and it seems to do the right thing in my simple tests.

  • Is using >- any different to using >? What is the difference to |? – Zulakis Jan 10 '17 at 18:39
  • 3
    Using > by itself will result in the value ending with a newline, which may or may not be significant. Using >- avoids this terminal newline. | is a literal block (it preserves newlines), while > wraps text to a single line. For details, read the Scalars portion of the YAML spec. – larsks Jan 10 '17 at 19:14
  • if I am not mistaken this adds quotes which is fine as long as you want to use them. But how can it work if you could not use it? For example HEAP_SIZE=256 and I want to change it with HEAP_SIZE=128 hmm? obviously one way is to write HEAP_SIZE= itself manually to the replacement string but what if I wanted to re-use match? – yurtesen Jan 27 '20 at 19:25

Another solution would be to use named groups:

    dest: /usr/src/freepbx/installlib/installcommand.class.php
    regexp: '(?P<firstpart>\$amp_conf\[.AMPDBHOST.\] = .)localhost(.;)'
    replace: '\g<firstpart>{{ asterisk_db_host }}\2'

Inspired by http://www.handverdrahtet.org/2016/01/ansible-using-numbered-backreference.html

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.