wip
This commit is contained in:
parent
13e4ea67c9
commit
a15bdfa95f
7 changed files with 126 additions and 174 deletions
|
@ -1,34 +0,0 @@
|
|||
user www-data;
|
||||
worker_processes 10;
|
||||
|
||||
pid /var/run/nginx.pid;
|
||||
|
||||
|
||||
events {
|
||||
worker_connections 500;
|
||||
}
|
||||
|
||||
http {
|
||||
include /etc/nginx/mime.types;
|
||||
default_type application/octet-stream;
|
||||
charset UTF-8;
|
||||
override_charset on;
|
||||
|
||||
sendfile on;
|
||||
#tcp_nopush on;
|
||||
|
||||
keepalive_timeout 15;
|
||||
client_body_timeout 12;
|
||||
client_header_timeout 12;
|
||||
send_timeout 10;
|
||||
|
||||
access_log /var/log/nginx/access.log;
|
||||
error_log /var/log/nginx/error.log;
|
||||
|
||||
client_body_buffer_size 10K;
|
||||
client_header_buffer_size 1k;
|
||||
client_max_body_size 1M;
|
||||
large_client_header_buffers 2 1k;
|
||||
|
||||
include /etc/nginx/sites/*;
|
||||
}
|
|
@ -1,13 +0,0 @@
|
|||
server {
|
||||
listen 80 default_server;
|
||||
listen [::]:80 default_server;
|
||||
server_name _;
|
||||
|
||||
location /.well-known/acme-challenge/ {
|
||||
alias /var/lib/dehydrated/acme-challenges/;
|
||||
}
|
||||
|
||||
location / {
|
||||
return 404;
|
||||
}
|
||||
}
|
|
@ -1,6 +0,0 @@
|
|||
server {
|
||||
listen 127.0.0.1:22999 default_server;
|
||||
server_name _;
|
||||
|
||||
stub_status;
|
||||
}
|
|
@ -18,26 +18,11 @@ directories = {
|
|||
|
||||
files = {
|
||||
'/etc/nginx/nginx.conf': {
|
||||
'content_type': 'mako',
|
||||
'context': {
|
||||
'username': 'www-data',
|
||||
**node.metadata['nginx'],
|
||||
},
|
||||
'content': repo.libs.nginx.render_config(node.metadata.get('nginx/config')),
|
||||
'triggers': {
|
||||
'svc_systemd:nginx:restart',
|
||||
},
|
||||
},
|
||||
'/etc/nginx/sites/stub_status': {
|
||||
'triggers': {
|
||||
'svc_systemd:nginx:restart',
|
||||
},
|
||||
},
|
||||
'/etc/nginx/sites/000-port80.conf': {
|
||||
'source': 'port80.conf',
|
||||
'triggers': {
|
||||
'svc_systemd:nginx:restart',
|
||||
},
|
||||
},
|
||||
'/etc/nginx/fastcgi.conf': {
|
||||
'triggers': {
|
||||
'svc_systemd:nginx:restart',
|
||||
|
@ -61,18 +46,15 @@ svc_systemd = {
|
|||
},
|
||||
}
|
||||
|
||||
for vhost, config in node.metadata.get('nginx/vhosts', {}).items():
|
||||
files[f'/etc/nginx/sites/{vhost}'] = {
|
||||
'source': 'site_template',
|
||||
'content_type': 'mako',
|
||||
'context': {
|
||||
'create_access_log': config.get('access_log', node.metadata.get('nginx/access_log', False)),
|
||||
'php_version': node.metadata.get('php/version', ''),
|
||||
'vhost': vhost,
|
||||
'nameservers': node.metadata.get('nameservers'),
|
||||
**config,
|
||||
},
|
||||
'needs': set(),
|
||||
for name, config in {
|
||||
**node.metadata.get('nginx/default_vhosts'),
|
||||
**node.metadata.get('nginx/vhosts'),
|
||||
}.items():
|
||||
files[f'/etc/nginx/sites/{name}'] = {
|
||||
'content': repo.libs.nginx.render_config({
|
||||
'server': config,
|
||||
}),
|
||||
'needs': [],
|
||||
'needed_by': {
|
||||
'svc_systemd:nginx',
|
||||
'svc_systemd:nginx:restart',
|
||||
|
@ -81,47 +63,8 @@ for vhost, config in node.metadata.get('nginx/vhosts', {}).items():
|
|||
'svc_systemd:nginx:restart',
|
||||
},
|
||||
}
|
||||
|
||||
if not 'webroot' in config:
|
||||
directories[f'/var/www/{vhost}'] = {}
|
||||
|
||||
if node.has_bundle('zfs'):
|
||||
directories[f'/var/www/{vhost}']['needs'] = {
|
||||
'bundle:zfs',
|
||||
}
|
||||
|
||||
directories[f'/var/www/{vhost}'].update(config.get('webroot_config', {}))
|
||||
|
||||
if config.get('ssl', 'letsencrypt') == 'letsencrypt':
|
||||
files[f'/etc/nginx/sites/{vhost}']['needs'].add('action:letsencrypt_ensure-some-certificate_{}'.format(config['domain']))
|
||||
files[f'/etc/nginx/sites/{vhost}']['needed_by'].add('action:letsencrypt_update_certificates')
|
||||
|
||||
elif config.get('ssl', 'letsencrypt'):
|
||||
files[f'/etc/nginx/ssl/{vhost}.crt'] = {
|
||||
'content_type': 'mako',
|
||||
'source': 'ssl_template',
|
||||
'context': {
|
||||
'domain': config['ssl'],
|
||||
},
|
||||
'needed_by': {
|
||||
'svc_systemd:nginx',
|
||||
'svc_systemd:nginx:restart',
|
||||
},
|
||||
'triggers': {
|
||||
'svc_systemd:nginx:reload',
|
||||
},
|
||||
}
|
||||
files[f'/etc/nginx/ssl/{vhost}.key'] = {
|
||||
'content': repo.vault.decrypt_file('ssl/{}.key.pem.vault'.format(config['ssl'])),
|
||||
'mode': '0600',
|
||||
'needed_by': {
|
||||
'svc_systemd:nginx',
|
||||
'svc_systemd:nginx:restart',
|
||||
},
|
||||
'triggers': {
|
||||
'svc_systemd:nginx:reload',
|
||||
},
|
||||
}
|
||||
|
||||
files[f'/etc/nginx/sites/{vhost}']['needs'].add(f'file:/etc/nginx/ssl/{vhost}.crt')
|
||||
files[f'/etc/nginx/sites/{vhost}']['needs'].add(f'file:/etc/nginx/ssl/{vhost}.key')
|
||||
|
||||
if name in node.metadata.get('letsencrypt/domains'):
|
||||
files[f'/etc/nginx/sites/{name}']['needs'].append(
|
||||
f'action:letsencrypt_ensure-some-certificate_{name}',
|
||||
)
|
||||
|
|
|
@ -7,63 +7,101 @@ defaults = {
|
|||
},
|
||||
},
|
||||
'nginx': {
|
||||
'worker_connections': 768,
|
||||
'config': {
|
||||
'user': 'www-data',
|
||||
'worker_processes': 10,
|
||||
'pid': '/var/run/nginx.pid',
|
||||
'events': {
|
||||
'worker_connections': 768,
|
||||
},
|
||||
'http': {
|
||||
'include': [
|
||||
'/etc/nginx/mime.types',
|
||||
'/etc/nginx/sites/*',
|
||||
],
|
||||
'default_type': 'application/octet-stream',
|
||||
'sendfile': 'on',
|
||||
'tcp_nopush': 'on',
|
||||
'server_names_hash_bucket_size': 128,
|
||||
'access_log': '/var/log/nginx/access.log',
|
||||
'error_log': '/var/log/nginx/error.log',
|
||||
},
|
||||
},
|
||||
'default_vhosts': {
|
||||
'80': {
|
||||
'listen': [
|
||||
'80',
|
||||
'[::]:80',
|
||||
],
|
||||
'location /.well-known/acme-challenge/': {
|
||||
'alias': '/var/lib/dehydrated/acme-challenges/',
|
||||
},
|
||||
'location /': {
|
||||
'return': '301 https://$host$request_uri',
|
||||
},
|
||||
},
|
||||
'stub_status': {
|
||||
'listen': '127.0.0.1:22999 default_server',
|
||||
'server_name': '_',
|
||||
'stub_status': '',
|
||||
},
|
||||
},
|
||||
'vhosts': {},
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
@metadata_reactor.provides(
|
||||
'nginx/vhosts',
|
||||
)
|
||||
def vhosts(metadata):
|
||||
vhosts = {}
|
||||
|
||||
for name, config in metadata.get('nginx/vhosts').items():
|
||||
vhosts[name] = {
|
||||
'server_name': name,
|
||||
'listen': [
|
||||
'443 ssl http2',
|
||||
'[::]:443 ssl http2',
|
||||
],
|
||||
'ssl_certificate': f'/var/lib/dehydrated/certs/{name}/fullchain.pem',
|
||||
'ssl_certificate_key': f'/var/lib/dehydrated/certs/{name}/privkey.pem',
|
||||
'location /.well-known/acme-challenge/': {
|
||||
'alias': '/var/lib/dehydrated/acme-challenges/',
|
||||
},
|
||||
}
|
||||
|
||||
return {
|
||||
'nginx': {
|
||||
'vhosts': vhosts,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@metadata_reactor.provides(
|
||||
'dns',
|
||||
)
|
||||
def dns(metadata):
|
||||
dns = {}
|
||||
|
||||
for config in metadata.get('nginx/vhosts', {}).values():
|
||||
dns[config['domain']] = {
|
||||
'A': [
|
||||
str(ip_interface(network['ipv4']).ip)
|
||||
for network in metadata.get('network').values()
|
||||
if 'ipv4' in network
|
||||
],
|
||||
'AAAA': [
|
||||
str(ip_interface(network['ipv6']).ip)
|
||||
for network in metadata.get('network').values()
|
||||
if 'ipv6' in network
|
||||
],
|
||||
}
|
||||
|
||||
return {
|
||||
'dns': dns,
|
||||
'dns': {
|
||||
domain: repo.libs.dns.get_a_records(metadata)
|
||||
for domain in metadata.get('nginx/vhosts')
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
@metadata_reactor.provides(
|
||||
'letsencrypt/domains',
|
||||
'letsencrypt/reload_after',
|
||||
'nginx/vhosts',
|
||||
)
|
||||
def letsencrypt(metadata):
|
||||
if not node.has_bundle('letsencrypt'):
|
||||
raise DoNotRunAgain
|
||||
|
||||
domains = {}
|
||||
vhosts = {}
|
||||
|
||||
for vhost, config in metadata.get('nginx/vhosts', {}).items():
|
||||
if config.get('ssl', 'letsencrypt') == 'letsencrypt':
|
||||
domain = config.get('domain', vhost)
|
||||
domains[domain] = config.get('domain_aliases', set())
|
||||
vhosts[vhost] = {
|
||||
'ssl': 'letsencrypt',
|
||||
}
|
||||
|
||||
return {
|
||||
'letsencrypt': {
|
||||
'domains': domains,
|
||||
'domains': {
|
||||
domain: {} for domain in metadata.get('nginx/vhosts')
|
||||
},
|
||||
'reload_after': {
|
||||
'nginx',
|
||||
},
|
||||
},
|
||||
'nginx': {
|
||||
'vhosts': vhosts,
|
||||
},
|
||||
}
|
||||
|
|
|
@ -20,14 +20,6 @@ defaults = {
|
|||
'php-zip': {},
|
||||
},
|
||||
},
|
||||
'nginx': {
|
||||
'vhosts': {
|
||||
'roundcube': {
|
||||
'webroot': '/opt/roundcube',
|
||||
'php': True,
|
||||
},
|
||||
},
|
||||
},
|
||||
'roundcube': {
|
||||
'database': {
|
||||
'provider': 'pgsql',
|
||||
|
@ -57,14 +49,19 @@ defaults = {
|
|||
}
|
||||
|
||||
@metadata_reactor.provides(
|
||||
'nginx/vhosts/roundcube/domain'
|
||||
'nginx/vhosts'
|
||||
)
|
||||
def domain(metadata):
|
||||
def vhost(metadata):
|
||||
return {
|
||||
'nginx': {
|
||||
'vhosts': {
|
||||
'roundcube': {
|
||||
'domain': metadata.get('mailserver/hostname'),
|
||||
metadata.get('mailserver/hostname'): {
|
||||
'root': '/opt/roundcube',
|
||||
'location ~ \.php$': {
|
||||
'include': 'fastcgi.conf',
|
||||
'fastcgi_split_path_info': '^(.+\.php)(/.+)$',
|
||||
'fastcgi_pass': f"unix:/run/php/php{metadata.get('php/version')}-fpm.sock",
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
|
|
27
libs/nginx.py
Normal file
27
libs/nginx.py
Normal file
|
@ -0,0 +1,27 @@
|
|||
def render_config(config):
|
||||
return '\n'.join(render_lines(config))
|
||||
|
||||
def render_lines(config, indent=0):
|
||||
lines = []
|
||||
blocks = []
|
||||
|
||||
for key, value in sorted(config.items()):
|
||||
if isinstance(value, dict):
|
||||
blocks.extend([
|
||||
'',
|
||||
key+' {',
|
||||
*render_lines(value, indent=4),
|
||||
'}',
|
||||
])
|
||||
elif isinstance(value, list):
|
||||
lines.extend([
|
||||
f'{key} {_value};' for _value in value
|
||||
])
|
||||
else:
|
||||
lines.append(
|
||||
f'{key} {value};'
|
||||
)
|
||||
|
||||
return [
|
||||
f"{' '*indent}{line}" for line in lines+blocks
|
||||
]
|
Loading…
Reference in a new issue