1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
|
---
- name: Precheck rabbitmq configuration
ansible.builtin.import_role:
name: service-precheck
vars:
service_precheck_services: "{{ rabbitmq_services }}"
service_name: "{{ project_name }}"
- name: Get container facts
become: true
kolla_container_facts:
action: get_containers
container_engine: "{{ kolla_container_engine }}"
name:
- rabbitmq
check_mode: false
register: container_facts
- name: Checking free port for RabbitMQ
ansible.builtin.wait_for:
host: "{{ api_interface_address }}"
port: "{{ rabbitmq_port }}"
connect_timeout: 1
timeout: 1
state: stopped
when:
- container_facts.containers['rabbitmq'] is not defined
- inventory_hostname in groups['rabbitmq']
- name: Checking free port for RabbitMQ Management
ansible.builtin.wait_for:
host: "{{ api_interface_address }}"
port: "{{ rabbitmq_management_port }}"
connect_timeout: 1
timeout: 1
state: stopped
when:
- container_facts.containers['rabbitmq'] is not defined
- inventory_hostname in groups['rabbitmq']
- name: Checking free port for RabbitMQ Cluster
ansible.builtin.wait_for:
host: "{{ api_interface_address }}"
port: "{{ rabbitmq_cluster_port }}"
connect_timeout: 1
timeout: 1
state: stopped
when:
- container_facts.containers['rabbitmq'] is not defined
- inventory_hostname in groups['rabbitmq']
- name: Checking free port for RabbitMQ EPMD
ansible.builtin.wait_for:
host: "{{ api_interface_address }}"
port: "{{ rabbitmq_epmd_port }}"
connect_timeout: 1
timeout: 1
state: stopped
when:
- container_facts.containers['rabbitmq'] is not defined
- inventory_hostname in groups['rabbitmq']
- name: Check if all rabbit hostnames are resolvable
vars:
nss_database: "{{ 'ahostsv4' if api_address_family == 'ipv4' else 'ahostsv6' }}"
ansible.builtin.command: "getent {{ nss_database }} {{ hostvars[item].ansible_facts.hostname }}"
changed_when: false
check_mode: false
register: rabbitmq_hostnames
with_items: "{{ groups['rabbitmq'] }}"
- name: Check if each rabbit hostname resolves uniquely to the proper IP address
ansible.builtin.fail:
msg: Hostname has to resolve uniquely to the IP address of api_interface
with_subelements:
- "{{ rabbitmq_hostnames.results }}"
- stdout_lines
when:
- not item.1 is match('^'+('api' | kolla_address(item.0.item))+'\\b')
- name: Check if TLS certificate exists for RabbitMQ
ansible.builtin.assert:
that: cert | length > 0
fail_msg: No TLS certificate provided for RabbitMQ.
vars:
cert: "{{ query('first_found', paths, errors='ignore') }}"
paths:
- "{{ kolla_certificates_dir }}/{{ inventory_hostname }}/rabbitmq-cert.pem"
- "{{ kolla_certificates_dir }}/{{ inventory_hostname }}-cert.pem"
- "{{ kolla_certificates_dir }}/rabbitmq-cert.pem"
- "{{ kolla_tls_backend_cert }}"
when:
- not kolla_externally_managed_cert | bool
- rabbitmq_enable_tls | bool
- name: Check if TLS key exists for RabbitMQ
ansible.builtin.assert:
that: key | length > 0
fail_msg: No TLS key provided for RabbitMQ.
vars:
key: "{{ query('first_found', paths, errors='ignore') }}"
paths:
- "{{ kolla_certificates_dir }}/{{ inventory_hostname }}/rabbitmq-key.pem"
- "{{ kolla_certificates_dir }}/{{ inventory_hostname }}-key.pem"
- "{{ kolla_certificates_dir }}/rabbitmq-key.pem"
- "{{ kolla_tls_backend_key }}"
when:
- not kolla_externally_managed_cert | bool
- rabbitmq_enable_tls | bool
- name: Check RabbitMQ HA compatibility
run_once: true
when:
- container_facts.containers['rabbitmq'] is defined
tags: rabbitmq-ha-precheck
block:
- name: List RabbitMQ queues
become: true
ansible.builtin.command: "{{ kolla_container_engine }} exec rabbitmq rabbitmqctl list_queues --silent name type --formatter json"
register: rabbitmq_queues
changed_when: false
check_mode: false
- name: Check if RabbitMQ quorum queues need to be configured
ansible.builtin.assert:
that: "{{ item.type == 'quorum' }}"
fail_msg: >
{{ item.name }} is a non-quorum queue.
Currently the procedure to migrate to quorum queues is manual.
Please follow the process described here: https://docs.openstack.org/kolla-ansible/latest/reference/message-queues/rabbitmq.html#high-availability.
Note that this process may take several hours on larger systems, and may cause a degradation in performance at large scale.
loop: "{{ (rabbitmq_queues.stdout | from_json) if rabbitmq_queues is not skipped else [] }}"
loop_control:
label: "{{ item.name }}"
when: not (item.name is search('reply_') or item.name is search('_fanout'))
- name: Check if RabbitMQ quorum queues for transient queues need to be configured
ansible.builtin.assert:
that: "{{ item.type == 'quorum' }}"
fail_msg: >
{{ item.name }} is a non-quorum queue.
Currently the procedure to migrate to quorum queues is manual.
Please follow the process described here: https://docs.openstack.org/kolla-ansible/latest/reference/message-queues/rabbitmq.html#high-availability.
Note that this process may take several hours on larger systems, and may cause a degradation in performance at large scale.
loop: "{{ (rabbitmq_queues.stdout | from_json) if rabbitmq_queues is not skipped else [] }}"
loop_control:
label: "{{ item.name }}"
when:
- item.name is search('reply_') or (item.name is search('_fanout') and not om_enable_rabbitmq_stream_fanout | bool)
- name: Check if RabbitMQ streams need to be configured
ansible.builtin.assert:
that: "{{ item.type == 'stream' }}"
fail_msg: >
om_enable_rabbitmq_stream_fanout is True but {{ item.name }} is not a stream.
Currently the procedure to migrate to streams is manual.
Please follow the process described here: https://docs.openstack.org/kolla-ansible/latest/reference/message-queues/rabbitmq.html#high-availability.
Note that this process may take several hours on larger systems.
If you do not wish to enable this feature, set om_enable_rabbitmq_stream_fanout to False.
loop: "{{ (rabbitmq_queues.stdout | from_json) if rabbitmq_queues is not skipped else [] }}"
loop_control:
label: "{{ item.name }}"
when:
- item.name is search('_fanout')
- om_enable_rabbitmq_stream_fanout | bool
- name: Check if RabbitMQ stream queue policy variables are valid
when: om_enable_rabbitmq_stream_fanout | bool
block:
- name: Check if the value of rabbitmq_stream_max_segment_size_bytes is valid
ansible.builtin.assert:
that:
- rabbitmq_stream_max_segment_size_bytes is integer
- rabbitmq_stream_max_segment_size_bytes > 0
fail_msg: >
rabbitmq_stream_max_segment_size_bytes needs to be a positive integer.
Please check its value again.
- name: Check if the value of rabbitmq_stream_segment_max_age is valid
ansible.builtin.assert:
that:
- rabbitmq_stream_segment_max_age is string
- 'rabbitmq_stream_segment_max_age is regex("^[0-9]+[YMDhms]$")'
fail_msg: >
rabbitmq_stream_segment_max_age needs to have numeric string that ends with one of the units in [Y, M, D, h, m, s].
Please check its value again.
|