instance-kedifa.cfg.in 12.3 KB
Newer Older
1
{%- if instance_parameter_dict['slap-software-type'] == software_type -%}
2 3 4 5
{% import "caucase" as caucase with context %}
# KeDiFa instance profile
[buildout]
extends =
6 7 8
  {{ software_parameter_dict['profile_common'] }}
  {{ software_parameter_dict['profile_monitor'] }}
  {{ software_parameter_dict['profile_logrotate_base'] }}
9 10

parts =
11
  monitor-base
12 13
  directory
  kedifa
14
  logrotate-entry-kedifa
15
  promise-kedifa-http-reply
16 17 18 19
  slave-kedifa-information
  caucased
  caucased-promise
  caucase-updater
20
  expose-csr_id
21
  promise-expose-csr_id-ip-port
22
  promise-logrotate-setup
23

24 25 26 27
[monitor-instance-parameter]
# Note: Workaround for monitor stack, which uses monitor-httpd-port parameter
#       directly, and in our case it can come from the network, thus resulting
#       with need to strip !py!'u'
28 29
monitor-httpd-port = {{ instance_parameter_dict['configuration.monitor-httpd-port'] | int }}
password = {{ instance_parameter_dict['configuration.monitor-password'] | string }}
30

31
[caucased]
32
hash-existing-files = ${buildout:directory}/software_release/buildout.cfg
33

34 35
{%  set caucase_host = '[' ~ instance_parameter_dict['ipv6-random'] ~ ']' %}
{%  set caucase_netloc = caucase_host ~ ':' ~ instance_parameter_dict['configuration.caucase_port'] -%}
36 37 38
{%  set caucase_url = 'http://' ~ caucase_netloc -%}
{{  caucase.caucased(
      prefix='caucased',
39
      buildout_bin_directory=software_parameter_dict['bin_directory'],
40 41 42 43
      caucased_path='${directory:service}/caucased',
      backup_dir='${directory:backup-caucased}',
      data_dir='${directory:caucased}',
      netloc=caucase_netloc,
44
      tmp='${directory:tmp}',
45 46
      service_auto_approve_count=0,
      user_auto_approve_count=1,
47
      key_len=2048
48 49 50 51 52 53 54 55 56 57
)}}

# Create all needed directories
[directory]
recipe = slapos.cookbook:mkdirectory

bin = ${buildout:directory}/bin/
etc = ${buildout:directory}/etc/
srv = ${buildout:directory}/srv/
var = ${buildout:directory}/var/
58
tmp = ${buildout:directory}/tmp/
59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76

backup = ${:srv}/backup
log = ${:var}/log
run = ${:var}/run
service = ${:etc}/service
etc-run = ${:etc}/run

# KeDiFa directories
kedifa = ${:srv}/kedifa
etc-kedifa = ${:etc}/kedifa

# CAUCASE directories
caucased = ${:srv}/caucased
backup-caucased = ${:backup}/caucased

# reservation
reservation = ${:srv}/reservation

77 78
# csr_id publication
csr_id = ${:srv}/csr_id
79 80
certificate-csr_id = ${:var}/certificate-csr_id
expose-csr_id-var = ${:var}/expose-csr_id
81

82 83 84 85 86
[kedifa-csr]
recipe = plone.recipe.command
organization = {{ slapparameter_dict['cluster-identification'] }}
organizational_unit = Kedifa Partition
command =
87
  if [ ! -f ${:template-csr} ] && [ ! -f ${:key} ]  ; then
88
    /bin/bash -c '{{ software_parameter_dict['openssl'] }} req -new -sha256 \
89 90 91
      -newkey rsa:2048 -nodes -keyout ${:key} \
      -subj "/O=${:organization}/OU=${:organizational_unit}" \
      -reqexts SAN \
92
      -config <(cat {{ software_parameter_dict['openssl_cnf'] }} \
93
      <(printf "\n[SAN]\nsubjectAltName=IP:${kedifa-config:ip}")) \
94
      -out ${:template-csr}'
95 96
  fi
update-command = ${:command}
97
template-csr = ${kedifa-config:template-csr}
98
key = ${kedifa-config:key}
99
{#- Can be stopped on error, as does not rely on self provided service #}
100 101 102 103
stop-on-error = True

{{ caucase.updater(
     prefix='caucase-updater',
104
     buildout_bin_directory=software_parameter_dict['bin_directory'],
105 106 107 108 109 110 111
     updater_path='${directory:service}/caucase-updater',
     url=caucase_url,
     data_dir='${directory:srv}/caucase-updater',
     crt_path='${kedifa-config:certificate}',
     ca_path='${kedifa-config:ca-certificate}',
     crl_path='${kedifa-config:crl}',
     key_path='${kedifa-csr:key}',
112
     on_renew='${kedifa-reloader:rendered}',
113
     template_csr='${kedifa-csr:template-csr}'
114 115
)}}

116 117 118 119 120 121 122 123 124
[store-csr_id]
recipe = plone.recipe.command

csr_id_path = ${directory:csr_id}/csr_id.txt
csr_work_path = ${directory:tmp}/${:_buildout_section_name_}

stop-on-error = False
update-command = ${:command}
command =
125
  {{ software_parameter_dict['bin_directory'] }}/caucase \
126 127 128 129 130 131 132 133 134 135 136
    --ca-url {{ caucase_url }} \
    --ca-crt ${kedifa-config:ca-certificate} \
    --crl ${kedifa-config:crl} \
    --mode service \
{#- XXX: Need to use caucase-updater-csr:csr, as there is no way to obatin csr_id from caucase-updater -#}
{#- XXX: nor directly path to the generated CSR #}
    --send-csr ${caucase-updater-csr:csr} > ${:csr_work_path} && \
  cut -d ' ' -f 1 ${:csr_work_path} > ${:csr_id_path}

[certificate-csr_id]
recipe = plone.recipe.command
137 138
certificate = ${directory:certificate-csr_id}/certificate.pem
key = ${directory:certificate-csr_id}/key.pem
139

140
{#- Can be stopped on error, as does not rely on self provided service #}
141 142 143 144
stop-on-error = True
update-command = ${:command}
command =
  if ! [ -f ${:key} ] && ! [ -f ${:certificate} ] ; then
145
    {{ software_parameter_dict['openssl'] }} req -new -newkey rsa:2048 -sha256 -subj \
146
      "/O=${kedifa-csr:organization}/OU=${kedifa-csr:organizational_unit}/CN={{ instance_parameter_dict['ipv6-random'] }}" \
147 148 149 150
      -days 5 -nodes -x509 -keyout ${:key} -out ${:certificate}
  fi

[expose-csr_id-configuration]
151
ip = {{ instance_parameter_dict['ipv6-random'] }}
152 153 154 155 156 157 158
port = 17000
key = ${certificate-csr_id:key}
certificate = ${certificate-csr_id:certificate}
error-log = ${directory:log}/expose-csr_id.log

[expose-csr_id-template]
recipe = slapos.recipe.template:jinja2
159 160 161
var = ${directory:expose-csr_id-var}
pid = ${directory:var}/nginx-expose-csr_id.pid
rendered = ${directory:etc}/nginx-expose-csr_id.conf
162
template = inline:
163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191
  daemon off;
  pid ${:pid};
  error_log ${expose-csr_id-configuration:error-log};
  events {
  }
  http {
    include {{ software_parameter_dict['nginx_mime'] }};
    server {
      server_name_in_redirect off;
      port_in_redirect off;
      error_log ${expose-csr_id-configuration:error-log};
      access_log /dev/null;
      listen [${expose-csr_id-configuration:ip}]:${expose-csr_id-configuration:port} ssl;
      ssl_certificate ${expose-csr_id-configuration:certificate};
      ssl_certificate_key ${expose-csr_id-configuration:key};
      default_type application/octet-stream;
      client_body_temp_path ${:var} 1 2;
      proxy_temp_path ${:var} 1 2;
      fastcgi_temp_path ${:var} 1 2;
      uwsgi_temp_path ${:var} 1 2;
      scgi_temp_path ${:var} 1 2;

      location / {
        alias ${directory:csr_id}/;
        autoindex off;
        sendfile on;
        sendfile_max_chunk 1m;
      }
    }
192 193
  }

194
[promise-expose-csr_id-ip-port]
195
<= monitor-promise-base
196
module = check_socket_listening
197
name = expose-csr_id-ip-port-listening.py
198
config-host = ${expose-csr_id-configuration:ip}
199 200
config-port = ${expose-csr_id-configuration:port}

201 202 203
[expose-csr_id]
depends = ${store-csr_id:command}
recipe = slapos.cookbook:wrapper
204 205
command-line = {{ software_parameter_dict['nginx'] }}
  -c ${expose-csr_id-template:rendered}
206 207

wrapper-path = ${directory:service}/expose-csr_id
208
hash-existing-files = ${buildout:directory}/software_release/buildout.cfg
209 210 211 212 213 214

[get-csr_id-certificate]
recipe = collective.recipe.shelloutput
commands =
  certificate = cat ${certificate-csr_id:certificate}

215 216 217 218
[jinja2-template-base]
recipe = slapos.recipe.template:jinja2
rendered = ${buildout:directory}/${:filename}
extra-context =
219
slapparameter_dict = {{ dumps(slapparameter_dict) }}
220
slap_software_type = {{ dumps(instance_parameter_dict['slap-software-type']) }}
221 222
context =
    import json_module json
223
    raw profile_common {{ software_parameter_dict['profile_common'] }}
224 225 226 227 228 229
    key slap_software_type :slap_software_type
    key slapparameter_dict :slapparameter_dict
    section directory directory
    ${:extra-context}

[kedifa-config]
230 231
ip = {{ instance_parameter_dict['ipv6-random'] }}
port = {{ instance_parameter_dict['configuration.kedifa_port'] }}
232 233 234
db = ${directory:kedifa}/kedifa.sqlite
certificate = ${directory:etc-kedifa}/certificate.pem
key = ${:certificate}
235
ca-certificate = ${directory:etc-kedifa}/ca-certificate.pem
236
crl = ${directory:etc-kedifa}/crl.pem
237
template-csr = ${directory:etc-kedifa}/template-csr.pem
238
pidfile = ${directory:run}/kedifa.pid
Łukasz Nowak's avatar
Łukasz Nowak committed
239
logfile = ${directory:log}/kedifa.log
240 241

[kedifa-reloader]
242
<= jinja2-template-base
243
template = {{ software_parameter_dict['template_wrapper'] }}
244 245 246 247 248 249
rendered = ${directory:etc-run}/kedifa-reloader
command =
  kill -HUP `cat ${kedifa-config:pidfile}`
mode = 0700
extra-context =
  key content :command
250

251
[promise-kedifa-http-reply]
252
<= monitor-promise-base
253 254
module = check_url_available
name = kedifa-http-reply.py
255
# Kedifa replies 400 on /, so use it to be sure that Kedifa replied
256
config-http-code = 400
257 258
config-url = https://[${kedifa-config:ip}]:${kedifa-config:port}
config-ca-cert-file = ${kedifa-config:ca-certificate}
259

260 261 262 263
[logrotate-entry-kedifa]
<= logrotate-entry-base
name = kedifa
log = ${kedifa-config:logfile}
264
rotate-num = {{ instance_parameter_dict['configuration.rotate-num'] | int }}
265
delaycompress =
266

267 268
[kedifa]
recipe = slapos.cookbook:wrapper
269
command-line = {{ software_parameter_dict['kedifa'] }}
270 271 272 273 274 275 276
  --ip ${kedifa-config:ip}
  --port ${kedifa-config:port}
  --db ${kedifa-config:db}
  --certificate ${kedifa-config:certificate}
  --ca-certificate ${kedifa-config:ca-certificate}
  --crl ${kedifa-config:crl}
  --pidfile ${kedifa-config:pidfile}
277
  --logfile ${kedifa-config:logfile}
278 279

wrapper-path = ${directory:service}/kedifa
280
hash-existing-files = ${buildout:directory}/software_release/buildout.cfg
281 282 283 284 285 286 287 288 289

# Publish KeDiFa configuration for upload and download for each slave
{%- set slave_kedifa_information = {} -%}
{%- for slave in slapparameter_dict['slave-list'] -%}
{%-   set slave_reference = slave['slave_reference'] -%}
{%-   set slave_dict = {} -%}
{%-   do slave_dict.__setitem__('key-generate-auth-url', 'https://[${kedifa-config:ip}]:${kedifa-config:port}/${%s-auth-random:passwd}/generateauth' % (slave_reference,)) -%}
{%-   do slave_dict.__setitem__('key-upload-url', 'https://[${kedifa-config:ip}]:${kedifa-config:port}/${%s-auth-random:passwd}?auth=' % (slave_reference,)) -%}
{%-   do slave_dict.__setitem__('key-download-url', 'https://[${kedifa-config:ip}]:${kedifa-config:port}/${%s-auth-random:passwd}' % (slave_reference,)) -%}
290
{%-   do slave_dict.__setitem__('kedifa-caucase-url', caucase_url ) -%}
291 292 293 294 295
{%-   do slave_kedifa_information.__setitem__(slave_reference, slave_dict) %}
[{{ slave_reference }}-auth-random-generate]
recipe = plone.recipe.command
file = ${directory:reservation}/${:_buildout_section_name_}
command =
296
  [ ! -f ${:file} ] && {{ software_parameter_dict['curl'] }}/bin/curl -s -g -X POST https://[${kedifa-config:ip}]:${kedifa-config:port}/reserve-id --cert ${kedifa-config:certificate} --cacert ${kedifa-config:ca-certificate} > ${:file}.tmp && mv ${:file}.tmp ${:file}
297 298 299 300 301 302 303 304 305 306 307 308 309 310
update-command = ${:command}

[{{ slave_reference }}-auth-random]
recipe = collective.recipe.shelloutput
file = {{ '${' + slave_reference }}-auth-random-generate:file}
commands =
  passwd = cat ${:file} 2>/dev/null || echo "NotReadyYet"

{% endfor %}

[master-auth-random-generate]
recipe = plone.recipe.command
file = ${directory:reservation}/${:_buildout_section_name_}
command =
311
  [ ! -f ${:file} ] && {{ software_parameter_dict['curl'] }}/bin/curl -s -g -X POST https://[${kedifa-config:ip}]:${kedifa-config:port}/reserve-id --cert ${kedifa-config:certificate} --cacert ${kedifa-config:ca-certificate} > ${:file}.tmp && mv ${:file}.tmp ${:file}
312 313 314 315 316 317 318 319 320 321
update-command = ${:command}

[master-auth-random]
recipe = collective.recipe.shelloutput
file = ${master-auth-random-generate:file}
commands =
  passwd = cat ${:file} 2>/dev/null || echo "NotReadyYet"

[slave-kedifa-information]
recipe = slapos.cookbook:publish.serialised
322 323
{# sort_keys are important in order to avoid shuffling parameters on each run #}
slave-kedifa-information = {{ json_module.dumps(slave_kedifa_information, sort_keys=True) }}
324 325 326 327
caucase-url = {{ caucase_url }}
master-key-generate-auth-url = https://[${kedifa-config:ip}]:${kedifa-config:port}/${master-auth-random:passwd}/generateauth
master-key-upload-url = https://[${kedifa-config:ip}]:${kedifa-config:port}/${master-auth-random:passwd}?auth=
master-key-download-url = https://[${kedifa-config:ip}]:${kedifa-config:port}/${master-auth-random:passwd}
328 329
csr_id-url = https://[${expose-csr_id-configuration:ip}]:${expose-csr_id-configuration:port}/csr_id.txt
csr_id-certificate = ${get-csr_id-certificate:certificate}
330
monitor-base-url = ${monitor-instance-parameter:monitor-base-url}
331 332 333 334 335 336 337 338

[promise-logrotate-setup]
<= monitor-promise-base
module = check_command_execute
name = ${:_buildout_section_name_}.py
config-command =
  ${logrotate:wrapper-path} -d

339
{%- endif -%} {# if instance_parameter_dict['slap-software-type'] == software_type #}