AnsibleShipyard / ansible-zookeeper

Ansible playbook for ZooKeeper
MIT License
95 stars 114 forks source link

How do you write your hosts? #23

Closed collinglass closed 8 years ago

collinglass commented 8 years ago

I'm getting this error:

fatal: [ec2-54-204-214-172.compute-1.amazonaws.com]: FAILED! => {"changed": false, "failed": true, "msg": "AnsibleUndefinedVariable: ERROR! 'unicode object' has no attribute 'host'"}
...

My hosts file is:

[mesos_primaries]
ec2-54-204-214-172.compute-1.amazonaws.com zoo_id=1 consul_bootstrap=true
ec2-54-235-59-210.compute-1.amazonaws.com zoo_id=2
ec2-54-83-161-83.compute-1.amazonaws.com zoo_id=3

How do I write my hosts file so it acknowledges the host name?

hinchliff commented 8 years ago

@collinglass In defaults, it says it has to be a List of dict (i.e. {zookeeper_hosts:[{host:,id:},{host:,id:},...]})

But I actually came here because I am having trouble dynamically creating (in jinja) a variable that holds a List of dict. The Ansible issue #10098 suggest that this is currently a bug in Ansible?

Is it possible to do this? Or should this project change to a different form of host specification?

This is some debug code I was using, which seems like it should work, except that Ansible is treating it as a string:

  - debug: var="
      {% set hosts = [] %}
      {% for node in groups.tag_zookeeper_master %}
        {% if hosts.append({
            'host':hostvars[node]['ansible_default_ipv4']['address'],
            'id':hostvars[node]['os__info']['metadata']['zookeeper_id']
        })%}
        {% endif %}
      {% endfor %}
      {{ hosts }}"

From which I get:

    "var": {
        "          [{'host': '172.16.54.14', 'id': u'1'}, {'host': '172.16.54.13', 'id': u'3'}, {'host': '172.16.54.12', 'id': u'2'}]": "          [{'host': '172.16.54.14', 'id': u'1'}, {'host': '172.16.54.13', 'id': u'3'}, {'host': '172.16.54.12', 'id': u'2'}]"
    }

Is there a better way to do this?

ninthnails commented 8 years ago

@collinglass @hinchliff This is how I did:

- hosts: zookeepers
  gather_facts: no
  vars:
    zookeeper_hosts: "
      {%- set ips = [] %}
      {%- for zk in groups['zookeepers'] %}
        {{- ips.append(dict(host=zk, id=loop.index)) }}
      {%- endfor %}
      {{- ips -}}
      "
  tasks:
    - debug: var=zookeeper_hosts

What I have found out is I had to use {{- ips.append... }} (note the {{) and use {{- ips -}} to make the assignment working. The dashes "-" are telling Jinja to strip leading or remaining white spaces when evaluating template. http://jinja.pocoo.org/docs/dev/templates/#whitespace-control

TASK [debug var=zookeeper_hosts] ***********************************************
ok: [zookeeper03.domain.net] => {
    "changed": false, 
    "zookeeper_hosts": [
        {
            "host": "zookeeper01.domain.net", 
            "id": 1
        }, 
        {
            "host": "zookeeper02.domain.net", 
            "id": 2
        }, 
        {
            "host": "zookeeper03.domain.net", 
            "id": 3
        }
    ]
}
ryoichitaniguchi commented 8 years ago

just fyi, I removed ".host" like below snippets(last 3line) in https://github.com/AnsibleShipyard/ansible-zookeeper/blob/master/templates/zoo.cfg.j2 then variable inventory_hostname are iterated(multiple hosts ok) instead but by design seems to be as described.

{% for server in zookeeper_hosts %}
server.{{loop.index}}={{server}}:2888:3888
{% endfor %}
ernestas-poskus commented 8 years ago

@ryoichitaniguchi @collinglass role now support both hash lists and array of hosts https://github.com/AnsibleShipyard/ansible-zookeeper/releases/tag/v0.9.2