question / help needed with conditionally passing variables to a module

43 views
Skip to first unread message

nrser

unread,
Apr 27, 2016, 2:12:35 AM4/27/16
to Ansible Project, ne...@beiarea.com
i have a role that can optionally be provided a rbenv_gem_version variable that should then be optionally provided to the gem module in it's tasks.

this seems very difficult to do with a large amount of copy-pasta due to modules differentiating between being passed null (Python None) and not being passed anything.

this is confusing because the Developing Modules docs state:

If required is false, you should document default, even if the default is ‘null’ (which is the default if no parameter is supplied). Make sure default parameter in docs matches default parameter in code.

the module is question is the gem module, and even though the optional version parameter does not have a specified default, i would infer from the above docs that it would default to null.

however, it seems like invoking

- gem:
    name
: lunchy

is different than

- gem:
    name
: lunchy
    version
: null

the later resulting in a bad command:

/Users/nrser/.rbenv/versions/2.1.6/bin/gem install --version None --no-user-install --no-document lunchy"


the pertinent parts of my role are as follows:


rbenv_gem_version: null


- name: "manage {{ rbenv_gem_name }} gem in rbenv rubies"
  gem:
    name: "{{ rbenv_gem_name }}"
    user_install: "{{ rbenv_gem_user_install }}"
    state: "{{ rbenv_gem_state }}"
    version: "{{ rbenv_gem_version }}"
    executable: "{{ ansible_env.HOME }}/.rbenv/versions/{{ item }}/bin/gem"
  when: item != 'system'
  with_items: "{{ rbenv_gem_rubies }}"


is there a way of fixing this besides this?

- name: "manage {{ rbenv_gem_name }} gem in rbenv rubies"
  gem:
    name: "{{ rbenv_gem_name }}"
    user_install: "{{ rbenv_gem_user_install }}"
    state: "{{ rbenv_gem_state }}"
    executable: "{{ ansible_env.HOME }}/.rbenv/versions/{{ item }}/bin/gem"
  when: rbenv_gem_version and (item != 'system')
  with_items: "{{ rbenv_gem_rubies }}"
  
- name: "manage {{ rbenv_gem_name }} gem in rbenv rubies"
  gem:
    name: "{{ rbenv_gem_name }}"
    user_install: "{{ rbenv_gem_user_install }}"
    state: "{{ rbenv_gem_state }}"
    version: "{{ rbenv_gem_version }}"
    executable: "{{ ansible_env.HOME }}/.rbenv/versions/{{ item }}/bin/gem"
  when: (not rbenv_gem_version) and (item != 'system')
  with_items: "{{ rbenv_gem_rubies }}"

besides being an annoying amount of copy-paste to maintain, this approach seems like it will spiral out of control with combinatoric complexity as a function of the number of optional variables in the module invocation.

thanks in advance, 

Neil.

Brian Coca

unread,
Apr 27, 2016, 5:23:03 PM4/27/16
to ansible...@googlegroups.com, ne...@beiarea.com
That is a documentation bug, the 'default' for version is actually  '' <= empty string.


----------
Brian Coca

nrser

unread,
Apr 28, 2016, 2:36:48 AM4/28/16
to Ansible Project, ne...@beiarea.com
so... is the empty string the default for all module params? or are you talking specifically about the version param in the gem module?

Brian Coca

unread,
Apr 28, 2016, 9:41:15 AM4/28/16
to ansible...@googlegroups.com, ne...@beiarea.com
Only version, the default can be set at each module, null/None is only if that module parameter does not specify one (in args spec, docs in this case are out of sync).


----------
Brian Coca

nrser

unread,
Apr 29, 2016, 3:08:27 AM4/29/16
to Ansible Project, ne...@beiarea.com
where would i see that? i'm looking here and it doesn't seem that any default is specified, just a type='str' and required=False: https://github.com/ansible/ansible-modules-core/blob/devel/packaging/language/gem.py#L222
Reply all
Reply to author
Forward
0 new messages