From c97ccd6a5f7330d88dfba94a8226948fb320cba6 Mon Sep 17 00:00:00 2001 From: Sam Yaple Date: Wed, 1 Jul 2015 17:23:13 +0000 Subject: [PATCH] Ansible Rabbitmq support Adds initial support for Rabbitmq in Ansible using the CONFIG_EXTERNAL methods. Additionally, this refactors some of the Rabbitmq config script to allow for reuse by CONFIG_EXTERNAL. Partially Implements: blueprint ansible-service Change-Id: I1765548f7e4f1258eb8a49e2a23242955f52655d --- .../roles/message-broker/defaults/main.yml | 22 +++++++ .../roles/message-broker/tasks/bootstrap.yml | 37 ++++++++++++ ansible/roles/message-broker/tasks/config.yml | 16 +++++ ansible/roles/message-broker/tasks/main.yml | 11 ++-- ansible/roles/message-broker/tasks/start.yml | 11 ++++ .../templates/rabbitmq-env.conf.j2 | 1 + .../templates/rabbitmq.config.j2 | 9 +++ ansible/roles/start.yml | 2 +- docker/centos/binary/rabbitmq/Dockerfile | 2 +- .../centos/binary/rabbitmq/config-external.sh | 1 + .../centos/binary/rabbitmq/config-internal.sh | 1 + .../centos/binary/rabbitmq/config-rabbit.sh | 58 +------------------ docker/common/rabbitmq/config-external.sh | 14 +++++ docker/common/rabbitmq/config-internal.sh | 10 ++++ docker/common/rabbitmq/config-rabbit.sh | 55 ++++++++++++++++++ docker/common/rabbitmq/start.sh | 22 ++++++- etc/kolla/passwords.yml | 8 +-- 17 files changed, 208 insertions(+), 72 deletions(-) create mode 100644 ansible/roles/message-broker/defaults/main.yml create mode 100644 ansible/roles/message-broker/tasks/bootstrap.yml create mode 100644 ansible/roles/message-broker/tasks/config.yml create mode 100644 ansible/roles/message-broker/tasks/start.yml create mode 100644 ansible/roles/message-broker/templates/rabbitmq-env.conf.j2 create mode 100644 ansible/roles/message-broker/templates/rabbitmq.config.j2 create mode 120000 docker/centos/binary/rabbitmq/config-external.sh create mode 120000 docker/centos/binary/rabbitmq/config-internal.sh mode change 100644 => 120000 docker/centos/binary/rabbitmq/config-rabbit.sh create mode 100644 docker/common/rabbitmq/config-external.sh create mode 100755 docker/common/rabbitmq/config-internal.sh create mode 100644 docker/common/rabbitmq/config-rabbit.sh diff --git a/ansible/roles/message-broker/defaults/main.yml b/ansible/roles/message-broker/defaults/main.yml new file mode 100644 index 0000000000..67dd88364a --- /dev/null +++ b/ansible/roles/message-broker/defaults/main.yml @@ -0,0 +1,22 @@ +--- +project_name: "rabbitmq" + +#################### +# Docker +#################### +docker_message_broker_registry: "{{ docker_registry }}" +docker_message_broker_namespace: "{{ docker_namespace }}" +kolla_message_broker_base_distro: "{{ kolla_base_distro }}" +kolla_message_broker_install_type: "{{ kolla_install_type }}" +kolla_message_broker_container_name: "rabbitmq" + +docker_message_broker_image: "{{ docker_message_broker_registry }}{{ docker_message_broker_namespace }}/{{ kolla_message_broker_base_distro }}-{{ kolla_message_broker_install_type }}-{{ kolla_message_broker_container_name }}" +docker_message_broker_tag: "{{ openstack_release }}" +docker_message_broker_image_full: "{{ docker_message_broker_image }}:{{ docker_message_broker_tag }}" + + +#################### +# Message-Broker +#################### +rabbitmq_user: "openstack" +rabbitmq_cluster_name: "openstack" diff --git a/ansible/roles/message-broker/tasks/bootstrap.yml b/ansible/roles/message-broker/tasks/bootstrap.yml new file mode 100644 index 0000000000..3cc2d51e51 --- /dev/null +++ b/ansible/roles/message-broker/tasks/bootstrap.yml @@ -0,0 +1,37 @@ +--- +# TODO(SamYaple): Improve check with a custom docker module to check if alive +- name: Checking if a rabbitmq_data exists + command: docker inspect rabbitmq_data + register: exists + changed_when: False + failed_when: False + always_run: True + +- include: ../../start.yml + vars: + container_command: "/bin/sleep infinity" + container_image: "{{ docker_message_broker_image_full }}" + container_name: "rabbitmq_data" + container_volumes: + - "/var/lib/rabbitmq/" + +- include: ../../start.yml + vars: + container_detach: "False" + container_environment: + KOLLA_BOOTSTRAP: + KOLLA_CONFIG_STRATEGY: "{{ config_strategy }}" + RABBITMQ_CLUSTER_COOKIE: "{{ rabbitmq_cluster_cookie }}" + container_image: "{{ docker_message_broker_image_full }}" + container_name: "rabbitmq_bootstrap" + container_volumes: + - "{{ node_config_directory }}/rabbitmq/:/opt/kolla/rabbitmq/:ro" + container_volumes_from: + - "rabbitmq_data" + when: exists.rc != 0 + +- name: Cleaning up boostrap container + docker: + image: "{{ docker_message_broker_image_full }}" + name: "rabbitmq_bootstrap" + state: "absent" diff --git a/ansible/roles/message-broker/tasks/config.yml b/ansible/roles/message-broker/tasks/config.yml new file mode 100644 index 0000000000..8c6caf5e53 --- /dev/null +++ b/ansible/roles/message-broker/tasks/config.yml @@ -0,0 +1,16 @@ +--- +- name: Ensuring config directory exists + file: + path: "{{ node_config_directory }}/rabbitmq/" + state: "directory" + recurse: "yes" + +- name: Copying over config(s) + template: + src: "{{ item.src }}" + dest: "{{ item.dest }}" + with_items: + - { src: "roles/message-broker/templates/rabbitmq-env.conf.j2", + dest: "{{ node_config_directory }}/rabbitmq/rabbitmq-env.conf" } + - { src: "roles/message-broker/templates/rabbitmq.config.j2", + dest: "{{ node_config_directory }}/rabbitmq/rabbitmq.config" } diff --git a/ansible/roles/message-broker/tasks/main.yml b/ansible/roles/message-broker/tasks/main.yml index c7a0fc8302..98daa4021c 100644 --- a/ansible/roles/message-broker/tasks/main.yml +++ b/ansible/roles/message-broker/tasks/main.yml @@ -1,7 +1,6 @@ --- -- name: Bringing up rabbitmq service(s) - docker_compose: - project_name: rabbitmq - compose_file: "{{ koalla_directory }}/compose/rabbitmq.yml" - command: up - no_recreate: true +- include: config.yml + +- include: bootstrap.yml + +- include: start.yml diff --git a/ansible/roles/message-broker/tasks/start.yml b/ansible/roles/message-broker/tasks/start.yml new file mode 100644 index 0000000000..4a75e0d944 --- /dev/null +++ b/ansible/roles/message-broker/tasks/start.yml @@ -0,0 +1,11 @@ +--- +- include: ../../start.yml + vars: + container_environment: + KOLLA_CONFIG_STRATEGY: "{{ config_strategy }}" + container_image: "{{ docker_message_broker_image_full }}" + container_name: "rabbitmq" + container_volumes: + - "{{ node_config_directory }}/rabbitmq/:/opt/kolla/rabbitmq/:ro" + container_volumes_from: + - "rabbitmq_data" diff --git a/ansible/roles/message-broker/templates/rabbitmq-env.conf.j2 b/ansible/roles/message-broker/templates/rabbitmq-env.conf.j2 new file mode 100644 index 0000000000..8921f227e4 --- /dev/null +++ b/ansible/roles/message-broker/templates/rabbitmq-env.conf.j2 @@ -0,0 +1 @@ +RABBITMQ_NODENAME=rabbit diff --git a/ansible/roles/message-broker/templates/rabbitmq.config.j2 b/ansible/roles/message-broker/templates/rabbitmq.config.j2 new file mode 100644 index 0000000000..e51d0c56dd --- /dev/null +++ b/ansible/roles/message-broker/templates/rabbitmq.config.j2 @@ -0,0 +1,9 @@ +[ + {rabbit, [ + {cluster_nodes, [{% for host in groups['database'] %}'rabbit@{{ hostvars[host]['ansible_hostname'] }}'{% if not loop.last %},{% endif %}{% endfor %}]}, + {default_user, <<"{{ rabbitmq_user }}">>}, + {default_pass, <<"{{ rabbitmq_password }}">>} + ]} +]. +% EOF + diff --git a/ansible/roles/start.yml b/ansible/roles/start.yml index 8aadfb3fc2..4925ba3635 100644 --- a/ansible/roles/start.yml +++ b/ansible/roles/start.yml @@ -13,7 +13,7 @@ docker: command: "{{ container_command | default(None) }}" detach: "{{ container_detach | default('True') }}" - env: "{{ container_environment | default(None) }}" + env: "{{ container_environment | default({}) }}" docker_api_version: "{{ docker_api_version }}" image: "{{ container_image }}" insecure_registry: "{{ docker_insecure_registry }}" diff --git a/docker/centos/binary/rabbitmq/Dockerfile b/docker/centos/binary/rabbitmq/Dockerfile index f42bc8307e..ba2d748b52 100644 --- a/docker/centos/binary/rabbitmq/Dockerfile +++ b/docker/centos/binary/rabbitmq/Dockerfile @@ -8,7 +8,7 @@ RUN yum -y install \ /usr/lib/rabbitmq/bin/rabbitmq-plugins enable rabbitmq_management COPY rabbitmq.config rabbitmq-env.conf /etc/rabbitmq/ -COPY config-rabbit.sh /opt/kolla/config-rabbit.sh +COPY config-rabbit.sh config-external.sh config-internal.sh /opt/kolla/ COPY start.sh /start.sh CMD ["/start.sh"] diff --git a/docker/centos/binary/rabbitmq/config-external.sh b/docker/centos/binary/rabbitmq/config-external.sh new file mode 120000 index 0000000000..e02e664c8e --- /dev/null +++ b/docker/centos/binary/rabbitmq/config-external.sh @@ -0,0 +1 @@ +../../../common/rabbitmq/config-external.sh \ No newline at end of file diff --git a/docker/centos/binary/rabbitmq/config-internal.sh b/docker/centos/binary/rabbitmq/config-internal.sh new file mode 120000 index 0000000000..73a13c7726 --- /dev/null +++ b/docker/centos/binary/rabbitmq/config-internal.sh @@ -0,0 +1 @@ +../../../common/rabbitmq/config-internal.sh \ No newline at end of file diff --git a/docker/centos/binary/rabbitmq/config-rabbit.sh b/docker/centos/binary/rabbitmq/config-rabbit.sh deleted file mode 100644 index 2be0f5b9c6..0000000000 --- a/docker/centos/binary/rabbitmq/config-rabbit.sh +++ /dev/null @@ -1,57 +0,0 @@ -#!/bin/bash - -. /opt/kolla/kolla-common.sh - -check_required_vars RABBITMQ_PASS RABBITMQ_USER - -RABBITMQ_CLUSTER_CONFIGURATION="" - -function configure_files { - - sed -i ' - s|@RABBITMQ_USER@|'"$RABBITMQ_USER"'|g - s|@RABBITMQ_PASS@|'"$RABBITMQ_PASS"'|g - s|@RABBITMQ_CLUSTER_CONFIGURATION@|'"$RABBITMQ_CLUSTER_CONFIGURATION"'|g - ' /etc/rabbitmq/rabbitmq.config - - sed -i ' - s|@RABBITMQ_LOG_BASE@|'"$RABBITMQ_LOG_BASE"'|g - ' /etc/rabbitmq/rabbitmq-env.conf -} - -function configure_cluster { - check_required_vars RABBITMQ_CLUSTER_COOKIE RABBITMQ_CLUSTER_NODES - - echo "${RABBITMQ_CLUSTER_COOKIE}" > /var/lib/rabbitmq/.erlang.cookie - chown rabbitmq /var/lib/rabbitmq/.erlang.cookie - chmod 700 /var/lib/rabbitmq/.erlang.cookie - - HOSTNAME="" - IP_ADDRESS="" - DELIMETER="" - - for node in ${RABBITMQ_CLUSTER_NODES}; do - HOSTNAME=`echo ${node} | cut -d'@' -f1` - IP_ADDRESS=`echo ${node} | cut -d'@' -f2` - CLUSTER_NODES="${CLUSTER_NODES}${DELIMETER}rabbit@${HOSTNAME}" - echo "${IP_ADDRESS} ${HOSTNAME}" >> /etc/hosts - DELIMETER="," - done - RABBITMQ_CLUSTER_CONFIGURATION="{cluster_nodes, {[$CLUSTER_NODES], disc}}," -} - -function configure_rabbit { - if [ "$RABBITMQ_CLUSTER_NODES" ] && [ "$RABBITMQ_CLUSTER_COOKIE" ]; then - configure_cluster - elif [ "$RABBITMQ_SERVICE_HOST" ]; then - # work around: - # https://bugs.launchpad.net/ubuntu/+source/rabbitmq-server/+bug/653405 - echo "${RABBITMQ_SERVICE_HOST} `/usr/bin/hostname -s`" > /etc/hosts - else - echo "You need RABBITMQ_SERVICE_HOST or RABBITMQ_CLUSTER_NODES & " \ - " RABBITMQ_CLUSTER_COOKIES variables" - exit 1 - fi - - configure_files -} diff --git a/docker/centos/binary/rabbitmq/config-rabbit.sh b/docker/centos/binary/rabbitmq/config-rabbit.sh new file mode 120000 index 0000000000..6feee2aba4 --- /dev/null +++ b/docker/centos/binary/rabbitmq/config-rabbit.sh @@ -0,0 +1 @@ +../../../common/rabbitmq/config-rabbit.sh \ No newline at end of file diff --git a/docker/common/rabbitmq/config-external.sh b/docker/common/rabbitmq/config-external.sh new file mode 100644 index 0000000000..40abd61569 --- /dev/null +++ b/docker/common/rabbitmq/config-external.sh @@ -0,0 +1,14 @@ +#!/bin/bash + +# Cluster configuration +if [[ -f /opt/kolla/rabbitmq/rabbitmq.config ]]; then + cp -af /opt/kolla/rabbitmq/rabbitmq.config /etc/rabbitmq/rabbitmq.config + chown rabbitmq: /etc/rabbitmq/rabbitmq.config + chmod 0600 /etc/rabbitmq/rabbitmq.config +fi + +if [[ -f /opt/kolla/rabbitmq/rabbitmq-env.conf ]]; then + cp -af /opt/kolla/rabbitmq/rabbitmq-env.conf /etc/rabbitmq/rabbitmq-env.conf + chown rabbitmq: /etc/rabbitmq/rabbitmq-env.conf + chmod 0600 /etc/rabbitmq/rabbitmq-env.conf +fi diff --git a/docker/common/rabbitmq/config-internal.sh b/docker/common/rabbitmq/config-internal.sh new file mode 100755 index 0000000000..8fc77f421f --- /dev/null +++ b/docker/common/rabbitmq/config-internal.sh @@ -0,0 +1,10 @@ +#!/bin/bash + +. /opt/kolla/kolla-common.sh +. /opt/kolla/config-rabbit.sh + +check_required_vars RABBITMQ_PASS RABBITMQ_USER + +configure_rabbit + +exec /usr/sbin/rabbitmq-server diff --git a/docker/common/rabbitmq/config-rabbit.sh b/docker/common/rabbitmq/config-rabbit.sh new file mode 100644 index 0000000000..750b253a47 --- /dev/null +++ b/docker/common/rabbitmq/config-rabbit.sh @@ -0,0 +1,55 @@ +#!/bin/bash + +RABBITMQ_CLUSTER_CONFIGURATION="" + +function configure_files { + sed -i ' + s|@RABBITMQ_USER@|'"$RABBITMQ_USER"'|g + s|@RABBITMQ_PASS@|'"$RABBITMQ_PASS"'|g + s|@RABBITMQ_CLUSTER_CONFIGURATION@|'"$RABBITMQ_CLUSTER_CONFIGURATION"'|g + ' /etc/rabbitmq/rabbitmq.config + + sed -i ' + s|@RABBITMQ_LOG_BASE@|'"$RABBITMQ_LOG_BASE"'|g + ' /etc/rabbitmq/rabbitmq-env.conf +} + +function set_rabbitmq_cookie { + echo "${RABBITMQ_CLUSTER_COOKIE}" > /var/lib/rabbitmq/.erlang.cookie + chown rabbitmq: /var/lib/rabbitmq/.erlang.cookie + chmod 400 /var/lib/rabbitmq/.erlang.cookie +} + +function configure_cluster { + check_required_vars RABBITMQ_CLUSTER_COOKIE RABBITMQ_CLUSTER_NODES + set_rabbitmq_cookie + + HOSTNAME="" + IP_ADDRESS="" + DELIMETER="" + + for node in ${RABBITMQ_CLUSTER_NODES}; do + HOSTNAME=`echo ${node} | cut -d'@' -f1` + IP_ADDRESS=`echo ${node} | cut -d'@' -f2` + CLUSTER_NODES="${CLUSTER_NODES}${DELIMETER}rabbit@${HOSTNAME}" + echo "${IP_ADDRESS} ${HOSTNAME}" >> /etc/hosts + DELIMETER="," + done + RABBITMQ_CLUSTER_CONFIGURATION="{cluster_nodes, {[$CLUSTER_NODES], disc}}," +} + +function configure_rabbit { + if [ "$RABBITMQ_CLUSTER_NODES" ] && [ "$RABBITMQ_CLUSTER_COOKIE" ]; then + configure_cluster + elif [ "$RABBITMQ_SERVICE_HOST" ]; then + # work around: + # https://bugs.launchpad.net/ubuntu/+source/rabbitmq-server/+bug/653405 + echo "${RABBITMQ_SERVICE_HOST} `/usr/bin/hostname -s`" > /etc/hosts + else + echo "You need RABBITMQ_SERVICE_HOST or RABBITMQ_CLUSTER_NODES & " \ + " RABBITMQ_CLUSTER_COOKIES variables" + exit 1 + fi + + configure_files +} diff --git a/docker/common/rabbitmq/start.sh b/docker/common/rabbitmq/start.sh index 4e76e382f9..8f7fef330d 100755 --- a/docker/common/rabbitmq/start.sh +++ b/docker/common/rabbitmq/start.sh @@ -1,7 +1,23 @@ #!/bin/bash -. /opt/kolla/config-rabbit.sh +set -o errexit -configure_rabbit +CMD="/usr/sbin/rabbitmq-server" +ARGS="" -exec /usr/sbin/rabbitmq-server +# loading common functions +source /opt/kolla/kolla-common.sh + +# config-internal script exec out of this function, it does not return here +set_configs + +# loading functions +source /opt/kolla/config-rabbit.sh + +# This catches all cases of the BOOTSTRAP variable being set, including empty +if [[ "${!KOLLA_BOOTSTRAP[@]}" ]]; then + set_rabbitmq_cookie + exit 0 +fi + +$CMD $ARGS diff --git a/etc/kolla/passwords.yml b/etc/kolla/passwords.yml index 79fa6868c1..8d2c9c9346 100644 --- a/etc/kolla/passwords.yml +++ b/etc/kolla/passwords.yml @@ -1,7 +1,6 @@ --- -# TODO: SamYaple -# This file should have generated values by default. Propose Ansible vault for -# locking down the secrets properly. +# TODO(SamYaple): This file should have generated values by default. Propose +# Ansible vault for locking down the secrets properly. ################### @@ -26,4 +25,5 @@ keystone_database_password: "password" #################### # RabbitMQ options #################### - +rabbitmq_password: "password" +rabbitmq_cluster_cookie: "password"