Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Backslashes in regex_replace #33202

Closed
kustodian opened this issue Nov 22, 2017 · 1 comment
Closed

Backslashes in regex_replace #33202

kustodian opened this issue Nov 22, 2017 · 1 comment
Labels
affects_2.5 This issue/PR affects Ansible v2.5 bug This issue/PR relates to a bug. support:core This issue/PR relates to code supported by the Ansible Engineering Team.

Comments

@kustodian
Copy link
Contributor

ISSUE TYPE
  • Bug?
COMPONENT NAME

Core

ANSIBLE VERSION
ansible 2.5.0 (devel 1ee511f82c) last updated 2017/11/22 20:37:38 (GMT +200)
SUMMARY

While I was upgrading from Ansible 2.3 to 2.4 I came across some changes in how backslashes are used to escape characters in regex_replace filter, so I made a little test playbook to show all the correct ways you can use backslashes. I told @abadger that I will make an issue for this, so here it is.

STEPS TO REPRODUCE

Here is a test playbook:

# fun_with_backslashes.yml
---
- hosts: localhost
  connection: local
  gather_facts: no
  vars:
    full_name: 'John Smith'
  tasks:
    - name: Backslashes msg in single quotes
      debug:
        msg: '{{ full_name | regex_replace("^([\S]+).*", "\1") }}'

    - name: Backslashes msg in double quotes
      debug:
        msg: "{{ full_name | regex_replace('^([\\S]+).*', '\\1') }}"

    - name: Backslashes with var using single quotes
      debug:
        var: full_name | regex_replace('^([\S]+).*', '\1')

    - name: Backslashes with var using double quotes
      debug:
        var: full_name | regex_replace("^([\S]+).*", "\1")

    - name: Backslashes in a template
      template:
        src: backslashes.j2
        dest: /tmp/backslashes
      check_mode: yes

    - name: Lookup template
      debug:
        msg: '{{ lookup("template", "backslashes.j2") }}'

and the template:

{# backslashes.j2 #}
{{ full_name | regex_replace("^([\\S]+).*", "\\1") }}
{{ full_name | regex_replace("^([\S]+).*", "\\1") }}
{% if full_name | regex_replace("^([\\S]+).*", "\\1") == 'John' %}
John
{% endif %}
{% if full_name | regex_replace("^([\S]+).*", "\\1") == 'John' %}
John
{% endif %}

These are all the combination I could think of that work correctly. The output of running this playbook (with -D to be able to see results of the template module):

$ ansible-playbook fun_with_backslashes.yml -D

PLAY [localhost] **********************************************************************************************************************************************************************************************

TASK [Backslashes msg in single quotes] ***********************************************************************************************************************************************************************
ok: [localhost] => {
    "msg": "John"
}

TASK [Backslashes msg in double quotes] ***********************************************************************************************************************************************************************
ok: [localhost] => {
    "msg": "John"
}

TASK [Backslashes with var using single quotes] ***************************************************************************************************************************************************************
ok: [localhost] => {
    "full_name | regex_replace('^([\\S]+).*', '\\1')": "John"
}

TASK [Backslashes with var using double quotes] ***************************************************************************************************************************************************************
ok: [localhost] => {
    "full_name | regex_replace(\"^([\\S]+).*\", \"\\1\")": "John"
}

TASK [Backslashes in a template] ******************************************************************************************************************************************************************************
--- before
+++ after: /tmp/tmpy3Q4hm/backslashes.j2
@@ -0,0 +1,4 @@
+John
+John
+John
+John

changed: [localhost]

TASK [Lookup template] ****************************************************************************************************************************************************************************************
ok: [localhost] => {
    "msg": "John\nJohn\nJohn\nJohn\n"
}
EXPECTED RESULTS

Results mostly look as expected:

  • Single backslash:
    • in YAML between single quotes
    • in YAML without quotes (doesn't matter if you use single or double quotes inside regex_replace)
  • Double backslash:
    • in YAML between double quotes
    • in templates
ACTUAL RESULTS

Only strange thing is that inside templates you can use both double and single quotes inside a regex, but you have to use double quotes for back reference, which means both of these lines work in templates

{{ full_name | regex_replace("^([\\S]+).*", "\\1") }}
{{ full_name | regex_replace("^([\S]+).*", "\\1") }}

In my opinion the second line feels like a bug and it should be consistent.

@ansibot ansibot added affects_2.5 This issue/PR affects Ansible v2.5 bug_report needs_triage Needs a first human triage before being processed. python3 support:core This issue/PR relates to code supported by the Ansible Engineering Team. labels Nov 22, 2017
@jborean93 jborean93 removed needs_triage Needs a first human triage before being processed. python3 labels Nov 22, 2017
@ansibot ansibot added bug This issue/PR relates to a bug. and removed bug_report labels Mar 1, 2018
@sivel
Copy link
Member

sivel commented May 10, 2019

This change was expected, and indicated in the 2.4 porting guide https://docs.ansible.com/ansible/latest/porting_guides/porting_guide_2.4.html#template-lookup-plugin-escaping-strings

@sivel sivel closed this as completed May 10, 2019
@ansible ansible locked and limited conversation to collaborators Aug 5, 2019
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
affects_2.5 This issue/PR affects Ansible v2.5 bug This issue/PR relates to a bug. support:core This issue/PR relates to code supported by the Ansible Engineering Team.
Projects
None yet
Development

No branches or pull requests

4 participants