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

Error message from lookup plugin #5059

Closed
oxyc opened this issue Nov 26, 2013 · 14 comments
Closed

Error message from lookup plugin #5059

oxyc opened this issue Nov 26, 2013 · 14 comments
Labels
bug This issue/PR relates to a bug. P2 Priority 2 - Issue Blocks Release

Comments

@oxyc
Copy link

oxyc commented Nov 26, 2013

playbook:

- host: development
  vars:
    hostname_v1: 'precise64'
    hostname_v2: '{{ ansible_hostname }}'

role task:

- debug: var=ansible_hostname
- debug: msg="{{ lookup('password', inventory_dir + '/credentials/' + ansible_hostname + '/root/mariadb_password length=15') }}"
- debug: var=hostname_v1
- debug: msg="{{ lookup('password', inventory_dir + '/credentials/' + hostname_v1 + '/root/mariadb_password length=15') }}"
- debug: var=hostname_v2
- debug: msg="{{ lookup('password', inventory_dir + '/credentials/' + hostname_v2 + '/root/mariadb_password length=15') }}"

Output:

TASK: [mariadb | debug var=ansible_hostname] ********************************** 
ok: [localhost] => {
    "ansible_hostname": "precise64", 
    "item": ""
}

TASK: [mariadb | debug msg="{{lookup('password', inventory_dir + '/credentials/' + ansible_hostname + '/root/mariadb_password length=15')}}"] *** 
ok: [localhost] => {
    "item": "", 
    "msg": "8_47E5O9AZO29aS"
}

TASK: [mariadb | debug var=hostname_v1] *************************************** 
ok: [localhost] => {
    "hostname_v1": "precise64", 
    "item": ""
}

TASK: [mariadb | debug msg="8_47E5O9AZO29aS"] ********************************* 
ok: [localhost] => {
    "item": "", 
    "msg": "8_47E5O9AZO29aS"
}

TASK: [mariadb | debug var=hostname_v2] *************************************** 
ok: [localhost] => {
    "hostname_v2": "precise64", 
    "item": ""
}
Traceback (most recent call last):
  File "/usr/bin/ansible-playbook", line 269, in <module>
    sys.exit(main(sys.argv[1:]))
  File "/usr/bin/ansible-playbook", line 209, in main
    pb.run()
  File "/usr/lib/python2.7/site-packages/ansible/playbook/__init__.py", line 263, in run
    if not self._run_play(play):
  File "/usr/lib/python2.7/site-packages/ansible/playbook/__init__.py", line 592, in _run_play
    if not self._run_task(play, task, False):
  File "/usr/lib/python2.7/site-packages/ansible/playbook/__init__.py", line 357, in _run_task
    self.callbacks.on_task_start(template(play.basedir, name, task.module_vars, lookup_fatal=False, filter_fatal=False), is_handler)
  File "/usr/lib/python2.7/site-packages/ansible/utils/template.py", line 319, in template
    varname = template_from_string(basedir, varname, vars, fail_on_undefined)
  File "/usr/lib/python2.7/site-packages/ansible/utils/template.py", line 541, in template_from_string
    res = jinja2.utils.concat(rf)
  File "<template>", line 11, in root
  File "/usr/lib/python2.7/site-packages/jinja2/runtime.py", line 193, in call
    return __obj(*args, **kwargs)
  File "/usr/lib/python2.7/site-packages/ansible/utils/template.py", line 532, in my_lookup
    return lookup(*args, basedir=basedir, **kwargs)
  File "/usr/lib/python2.7/site-packages/ansible/utils/template.py", line 89, in lookup
    ran = instance.run(*args, inject=vars, **kwargs)
  File "/usr/lib/python2.7/site-packages/ansible/runner/lookup_plugins/password.py", line 96, in run
    content = open(path).read().rstrip()
IOError: [Errno 21] Is a directory: u'/'
make: *** [all] Error 1
$ ansible --version
ansible 1.5
@mpdehaan
Copy link
Contributor

The error you have is from:

- debug: msg="{{ lookup('password', inventory_dir + '/credentials/' + hostname_v2 + '/root/mariadb_password length=15') }}"

Where it's saying something that is trying to open is a directory.

The description isn't accurate so I'll update it.

@mpdehaan
Copy link
Contributor

The original defect was saying variables aren't resolved inside lookup plugins.

This isn't universally the case, they are resolved.

It may be that "inventory_dir" is not resolved at this point, however.

To be determined and in queue for being reproduced.

Thanks!

@oxyc
Copy link
Author

oxyc commented Nov 26, 2013

inventory_dir is resolved correctly. However hostname_v2 is resolved into '{{ ansible_hostname }}' and not 'precise64'.

@mpdehaan
Copy link
Contributor

Ah, this is because of the indirect variable above. Gotcha.

@bcoca
Copy link
Member

bcoca commented Nov 27, 2013

names are evaluated early, so if you varaible comes from inventory or facts
it won't make it into names (which have to be the same across hosts).

@dominus-directus
Copy link

hi!
this simple play:

- debug: msg="{{lookup('file', '/home/il/src/ansible/roles/auth/files/file')}}"

- debug: msg="{{lookup('file', item)}}"
  with_items:
  - /home/il/src/ansible/roles/auth/files/file

doesn't work as expected:

PLAY [all] ******************************************************************** 

GATHERING FACTS *************************************************************** 
ok: [rtu0]

TASK: [auth | debug msg="content of the file"] ******************************** 
ok: [rtu0] => {
    "item": "", 
    "msg": "content of the file"
}
Traceback (most recent call last):
  File "/usr/bin/ansible-playbook", line 269, in <module>
    sys.exit(main(sys.argv[1:]))
  File "/usr/bin/ansible-playbook", line 209, in main
    pb.run()
  File "/usr/lib/pymodules/python2.7/ansible/playbook/__init__.py", line 263, in run
    if not self._run_play(play):
  File "/usr/lib/pymodules/python2.7/ansible/playbook/__init__.py", line 592, in _run_play
    if not self._run_task(play, task, False):
  File "/usr/lib/pymodules/python2.7/ansible/playbook/__init__.py", line 357, in _run_task
    self.callbacks.on_task_start(template(play.basedir, name, task.module_vars, lookup_fatal=False, filter_fatal=False), is_handler)
  File "/usr/lib/pymodules/python2.7/ansible/utils/template.py", line 319, in template
    varname = template_from_string(basedir, varname, vars, fail_on_undefined)
  File "/usr/lib/pymodules/python2.7/ansible/utils/template.py", line 541, in template_from_string
    res = jinja2.utils.concat(rf)
  File "<template>", line 10, in root
  File "/usr/lib/python2.7/dist-packages/jinja2/runtime.py", line 180, in call
    return __obj(*args, **kwargs)
  File "/usr/lib/pymodules/python2.7/ansible/utils/template.py", line 532, in my_lookup
    return lookup(*args, basedir=basedir, **kwargs)
  File "/usr/lib/pymodules/python2.7/ansible/utils/template.py", line 89, in lookup
    ran = instance.run(*args, inject=vars, **kwargs)
  File "/usr/lib/pymodules/python2.7/ansible/runner/lookup_plugins/file.py", line 42, in run
    ret.append(codecs.open(path, encoding="utf8").read().rstrip())
  File "/usr/lib/python2.7/codecs.py", line 881, in open
    file = __builtin__.open(filename, mode, buffering)
IOError: [Errno 21] Is a directory: '/home/il/src/ansible/roles/auth/files'

tried on 1.4 and 1.5

@dominus-directus
Copy link

hi!
Should I create different issue for above?
{{item}} resolution in any part of ansible is kind of "core functionality" IMHO.

@dominus-directus
Copy link

still not fixed in git head.

@jctanner
Copy link
Contributor

jctanner commented Mar 5, 2014

@dominus-directus please open a new bug for that.

@jctanner
Copy link
Contributor

jctanner commented Mar 5, 2014

@oxyc bug confirmed. It looks like ansible_hostname is not in the inject that is sent to the plugin, and it doesn't fill in the hostname correctly:

(Epdb) pp inject
{'always_run': False,
 'changed_when': None,
 'delegate_to': None,
 'failed_when': None,
 'hostname_v1': 'precise64',
 'hostname_v2': '{{ansible_hostname}}',
 'ignore_errors': False,
 'inventory_dir': '/home/jtanner/issues/5059-lookup-error',
 'playbook_dir': '.',
 'register': None}
(Epdb) utils.listify_lookup_plugin_terms(terms, self.basedir, inject)
u'/home/jtanner/issues/5059-lookup-error/credentials/{{ansible_hostname}}/password length=15'

@jctanner
Copy link
Contributor

jctanner commented Mar 5, 2014

The traceback occurs because the debug task has no name and defaults to something like ...

debug msg="{{lookup('password', inventory_dir + '/credentials/' + hostname_v2 + '/password length=15')}}"

This string is sent through to self.callbacks.on_task_start in playbook/init.py and subsequently causes the failure in password.py. A workaround is to name the task:

    - name: test
      debug: msg="{{ lookup('password', inventory_dir + '/credentials/' + hostname_v2 + '/password length=15') }}"

@jctanner
Copy link
Contributor

jctanner commented Mar 5, 2014

Preliminary patch:

diff --git a/lib/ansible/utils/template.py b/lib/ansible/utils/template.py
index fc4ff9f..12f72fe 100644
--- a/lib/ansible/utils/template.py
+++ b/lib/ansible/utils/template.py
@@ -88,8 +88,14 @@ def lookup(name, *args, **kwargs):
     vars = kwargs.get('vars', None)

     if instance is not None:
-        ran = instance.run(*args, inject=vars, **kwargs)
-        return ",".join(ran)
+        # safely catch run failures per #5059
+        try:
+            ran = instance.run(*args, inject=vars, **kwargs)
+        except Exception, e:
+            ran = None
+        if ran:
+            ran = ",".join(ran)
+        return ran
     else:
         raise errors.AnsibleError("lookup plugin (%s) not found" % name)

@mpdehaan mpdehaan added P3 and removed priority labels Mar 19, 2014
@jimi-c jimi-c assigned jctanner and unassigned jimi-c Mar 19, 2014
@jctanner
Copy link
Contributor

@oxyc this should be fixed by 2a976ac

@dominus-directus
Copy link

solved my issue too

@ansible ansible locked and limited conversation to collaborators Apr 24, 2019
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
bug This issue/PR relates to a bug. P2 Priority 2 - Issue Blocks Release
Projects
None yet
Development

No branches or pull requests

7 participants