qzwi: add LDAP
This commit is contained in:
parent
0e6fbd3e78
commit
471f8e8771
12 changed files with 412 additions and 1 deletions
45
bundles/openldap/files/etc-default-slapd
Normal file
45
bundles/openldap/files/etc-default-slapd
Normal file
|
@ -0,0 +1,45 @@
|
|||
# Default location of the slapd.conf file or slapd.d cn=config directory. If
|
||||
# empty, use the compiled-in default (/etc/ldap/slapd.d with a fallback to
|
||||
# /etc/ldap/slapd.conf).
|
||||
SLAPD_CONF=/etc/ldap/slapd.conf
|
||||
|
||||
# System account to run the slapd server under. If empty the server
|
||||
# will run as root.
|
||||
SLAPD_USER="openldap"
|
||||
|
||||
# System group to run the slapd server under. If empty the server will
|
||||
# run in the primary group of its user.
|
||||
SLAPD_GROUP="openldap"
|
||||
|
||||
# Path to the pid file of the slapd server. If not set the init.d script
|
||||
# will try to figure it out from $SLAPD_CONF (/etc/ldap/slapd.d by
|
||||
# default)
|
||||
SLAPD_PIDFILE=
|
||||
|
||||
# slapd normally serves ldap only on all TCP-ports 389. slapd can also
|
||||
# service requests on TCP-port 636 (ldaps) and requests via unix
|
||||
# sockets.
|
||||
# Example usage:
|
||||
# SLAPD_SERVICES="ldap://127.0.0.1:389/ ldaps:/// ldapi:///"
|
||||
SLAPD_SERVICES="ldap:/// ldapi:/// ldaps://0.0.0.0:636/"
|
||||
|
||||
# If SLAPD_NO_START is set, the init script will not start or restart
|
||||
# slapd (but stop will still work). Uncomment this if you are
|
||||
# starting slapd via some other means or if you don't want slapd normally
|
||||
# started at boot.
|
||||
#SLAPD_NO_START=1
|
||||
|
||||
# If SLAPD_SENTINEL_FILE is set to path to a file and that file exists,
|
||||
# the init script will not start or restart slapd (but stop will still
|
||||
# work). Use this for temporarily disabling startup of slapd (when doing
|
||||
# maintenance, for example, or through a configuration management system)
|
||||
# when you don't want to edit a configuration file.
|
||||
SLAPD_SENTINEL_FILE=/etc/ldap/noslapd
|
||||
|
||||
# For Kerberos authentication (via SASL), slapd by default uses the system
|
||||
# keytab file (/etc/krb5.keytab). To use a different keytab file,
|
||||
# uncomment this line and change the path.
|
||||
#export KRB5_KTNAME=/etc/krb5.keytab
|
||||
|
||||
# Additional options to pass to slapd
|
||||
SLAPD_OPTIONS=""
|
9
bundles/openldap/files/openssh-lpk_openldap.schema
Normal file
9
bundles/openldap/files/openssh-lpk_openldap.schema
Normal file
|
@ -0,0 +1,9 @@
|
|||
attributetype ( 1.3.6.1.4.1.24552.500.1.1.1.13 NAME 'sshPublicKey'
|
||||
DESC 'MANDATORY: OpenSSH Public key'
|
||||
EQUALITY octetStringMatch
|
||||
SYNTAX 1.3.6.1.4.1.1466.115.121.1.40 )
|
||||
|
||||
objectclass ( 1.3.6.1.4.1.24552.500.1.1.2.0 NAME 'ldapPublicKey' SUP top AUXILIARY
|
||||
DESC 'MANDATORY: OpenSSH LPK objectclass'
|
||||
MAY ( sshPublicKey $ uid )
|
||||
)
|
88
bundles/openldap/files/slapd.conf
Normal file
88
bundles/openldap/files/slapd.conf
Normal file
|
@ -0,0 +1,88 @@
|
|||
include /etc/ldap/schema/core.schema
|
||||
include /etc/ldap/schema/cosine.schema
|
||||
include /etc/ldap/schema/nis.schema
|
||||
include /etc/ldap/schema/inetorgperson.schema
|
||||
% for schema in sorted(conf.get('schemas', set())):
|
||||
include /etc/ldap/schema/${schema}.schema
|
||||
% endfor
|
||||
include /etc/ldap/schema/ppolicy.schema
|
||||
|
||||
pidfile /var/run/slapd/slapd.pid
|
||||
argsfile /var/run/slapd/slapd.args
|
||||
|
||||
# OpenLDAP logs can get rather spammy, so we enable logging only
|
||||
# on demand for debug purposes to keep the syslog nice and tidy.
|
||||
loglevel ${conf.get('loglevel', 0)}
|
||||
|
||||
sizelimit unlimited
|
||||
|
||||
disallow bind_anon
|
||||
|
||||
modulepath /usr/lib/ldap
|
||||
moduleload back_mdb.so
|
||||
moduleload back_monitor.so
|
||||
moduleload back_ldap.so
|
||||
moduleload memberof.so
|
||||
moduleload syncprov.so
|
||||
moduleload ppolicy.so
|
||||
moduleload pw-sha2.so
|
||||
|
||||
TLSCACertificateFile /etc/ldap/ssl/${conf['ssl']}.crt_intermediate.pem
|
||||
TLSCertificateFile /etc/ldap/ssl/${conf['ssl']}.crt.pem
|
||||
TLSCertificateKeyFile /etc/ldap/ssl/${conf['ssl']}.key.pem
|
||||
#TLSVerifyClient never
|
||||
#TLSCRLCheck none
|
||||
#security tls=1
|
||||
|
||||
backend mdb
|
||||
database mdb
|
||||
suffix "dc=qzwi,dc=de"
|
||||
checkpoint 32 30
|
||||
rootdn "uid=root,dc=qzwi,dc=de"
|
||||
rootpw ${conf['rootpw']}
|
||||
directory /var/lib/ldap
|
||||
# mdb has a limit:
|
||||
maxsize 1000000000
|
||||
|
||||
monitoring on
|
||||
|
||||
index cn pres,eq
|
||||
index dc pres,eq
|
||||
index member pres,eq
|
||||
index memberOf pres,eq
|
||||
index memberUid eq
|
||||
index objectClass eq
|
||||
index uid pres,eq
|
||||
|
||||
overlay memberof
|
||||
memberof-group-oc groupOfNames
|
||||
memberof-member-ad member
|
||||
memberof-memberof-ad memberOf
|
||||
memberof-refint TRUE
|
||||
|
||||
overlay ppolicy
|
||||
|
||||
#access to dn.one="ou=QZWI,dc=qzwi,dc=de"
|
||||
# attrs=userPassword
|
||||
# by anonymous auth
|
||||
# by * break
|
||||
|
||||
#access to * by group="ou=qzwi-admins,ou=Groups,dc=qzwi,dc=de" manage by * break
|
||||
|
||||
% for tree, matches in sorted(conf.get('access', {}).items()):
|
||||
# ${tree}
|
||||
% for access, user in sorted(matches.items()):
|
||||
access to dn.sub="${tree}" by dn.exact="${user}" ${access} by * break
|
||||
% endfor
|
||||
# / ${tree}
|
||||
|
||||
% endfor
|
||||
|
||||
# Grant read access to all applications
|
||||
#access to dn.children="ou=Applications,dc=qzwi,dc=de" attrs=userPassword by anonymous auth by * break
|
||||
#access to dn.sub="ou=People,dc=qzwi,dc=de" by dn.children="ou=Applications,dc=qzwi,dc=de" read by * break
|
||||
#access to dn.sub="ou=Groups,dc=qzwi,dc=de" by dn.children="ou=Applications,dc=qzwi,dc=de" read by * break
|
||||
|
||||
database monitor
|
||||
rootDN "cn=admin,cn=Monitor"
|
||||
rootPW admin
|
13
bundles/openldap/files/slapdump
Normal file
13
bundles/openldap/files/slapdump
Normal file
|
@ -0,0 +1,13 @@
|
|||
#!/bin/bash
|
||||
# ^^^^ Needed for fancy co-processes.
|
||||
|
||||
db=$1
|
||||
|
||||
[[ -z "$db" ]] && { echo "Usage: $0 <db>" >&2; exit 1; }
|
||||
|
||||
slapcat -b "$db" -f /etc/ldap/slapd.conf \
|
||||
1> >(gzip >/var/tmp/ldapdumps/"$db".gz) \
|
||||
2> >(grep -v \
|
||||
-e "no DB_CONFIG file found in directory" \
|
||||
-e "Expect poor performance" \
|
||||
>&2)
|
115
bundles/openldap/items.py
Normal file
115
bundles/openldap/items.py
Normal file
|
@ -0,0 +1,115 @@
|
|||
from re import sub
|
||||
|
||||
svc_systemd = {
|
||||
'slapd': {
|
||||
'needs': {
|
||||
'file:/etc/ldap/slapd.conf',
|
||||
'file:/etc/ldap/ssl/{}.crt.pem'.format(node.metadata.get('openldap/ssl')),
|
||||
'file:/etc/ldap/ssl/{}.crt_intermediate.pem'.format(node.metadata.get('openldap/ssl')),
|
||||
'file:/etc/ldap/ssl/{}.key.pem'.format(node.metadata.get('openldap/ssl')),
|
||||
'pkg_apt:slapd',
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
directories = {
|
||||
'/etc/ldap/ssl': {
|
||||
'purge': True,
|
||||
},
|
||||
}
|
||||
|
||||
files = {
|
||||
'/etc/default/slapd': {
|
||||
'source': 'etc-default-slapd',
|
||||
'triggers': {
|
||||
'svc_systemd:slapd:restart',
|
||||
},
|
||||
},
|
||||
'/etc/ldap/slapd.d': {
|
||||
'delete': True,
|
||||
'needs': {
|
||||
'pkg_apt:slapd',
|
||||
},
|
||||
},
|
||||
'/etc/ldap/slapd.conf': {
|
||||
'content_type': 'mako',
|
||||
'context': {
|
||||
'conf': node.metadata.get('openldap'),
|
||||
},
|
||||
'needs': {
|
||||
'pkg_apt:slapd',
|
||||
},
|
||||
'triggers': {
|
||||
'svc_systemd:slapd:restart',
|
||||
},
|
||||
},
|
||||
'/etc/ldap/ssl/{}.crt.pem'.format(node.metadata.get('openldap/ssl')): {
|
||||
'owner': 'openldap',
|
||||
'mode': '0440',
|
||||
# Those files can exist independently, but the private
|
||||
# key might come from a Fault and we must make sure to
|
||||
# put matching private and public keys on the system.
|
||||
'needs': {
|
||||
'file:/etc/ldap/ssl/{}.crt_intermediate.pem'.format(node.metadata.get('openldap/ssl')),
|
||||
'file:/etc/ldap/ssl/{}.key.pem'.format(node.metadata.get('openldap/ssl')),
|
||||
},
|
||||
'triggers': {
|
||||
'svc_systemd:slapd:restart',
|
||||
},
|
||||
'source': 'ssl/{}.crt.pem'.format(node.metadata.get('openldap/ssl')),
|
||||
},
|
||||
'/etc/ldap/ssl/{}.key.pem'.format(node.metadata.get('openldap/ssl')): {
|
||||
'owner': 'openldap',
|
||||
'mode': '0440',
|
||||
'content': repo.vault.decrypt_file('ssl/{}.key.pem.vault'.format(node.metadata.get('openldap/ssl'))),
|
||||
'needs': {
|
||||
'pkg_apt:slapd',
|
||||
},
|
||||
},
|
||||
'/etc/ldap/ssl/{}.crt_intermediate.pem'.format(node.metadata.get('openldap/ssl')): {
|
||||
'owner': 'openldap',
|
||||
'mode': '0440',
|
||||
# Those files can exist independently, but the private
|
||||
# key might come from a Fault and we must make sure to
|
||||
# put matching private and public keys on the system.
|
||||
'needs': {
|
||||
'file:/etc/ldap/ssl/{}.key.pem'.format(node.metadata.get('openldap/ssl')),
|
||||
},
|
||||
'source': 'ssl/{}.crt_intermediate.pem'.format(node.metadata.get('openldap/ssl')),
|
||||
},
|
||||
'/usr/local/sbin/slapdump': {
|
||||
'mode': '0755',
|
||||
},
|
||||
}
|
||||
|
||||
for schema in node.metadata.get('openldap/schemas', {}):
|
||||
files['/etc/ldap/schema/{}.schema'.format(schema)] = {
|
||||
'source': '{}.schema'.format(schema),
|
||||
'triggers': {
|
||||
'svc_systemd:slapd:restart',
|
||||
},
|
||||
}
|
||||
|
||||
directories = {
|
||||
'/var/tmp/ldapdumps': {
|
||||
'mode': '0700',
|
||||
},
|
||||
}
|
||||
|
||||
users = {
|
||||
'openldap': {
|
||||
'needs': {
|
||||
'pkg_apt:slapd',
|
||||
},
|
||||
'triggers': {
|
||||
'svc_systemd:slapd:restart',
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
for database in node.metadata.get('openldap/backup', set()):
|
||||
cleaned = sub('[^a-zA-Z0-9]', '_', database)
|
||||
files[f'/etc/backup-pre-hooks.d/50-ldapdump-{cleaned}'] = {
|
||||
'content': f'#!/bin/sh\n/usr/local/sbin/slapdump {database}\n',
|
||||
'mode': '0755',
|
||||
}
|
71
bundles/openldap/metadata.py
Normal file
71
bundles/openldap/metadata.py
Normal file
|
@ -0,0 +1,71 @@
|
|||
from bundlewrap.metadata import atomic
|
||||
|
||||
|
||||
defaults = {
|
||||
'apt': {
|
||||
'packages': {
|
||||
'db-util': {},
|
||||
'ldap-utils': {},
|
||||
'slapd': {},
|
||||
'slapd-contrib': {},
|
||||
},
|
||||
},
|
||||
'backups': {
|
||||
'paths': {
|
||||
# Create backups both from ZFS and from dumps. Because
|
||||
# they're cheap.
|
||||
'/var/lib/ldap',
|
||||
'/var/tmp/ldapdumps',
|
||||
},
|
||||
},
|
||||
'cron': {
|
||||
},
|
||||
'icinga2_api': {
|
||||
'openldap': {
|
||||
'services': {
|
||||
'OPENLDAP PROCESS': {
|
||||
'command_on_monitored_host': '/usr/lib/nagios/plugins/check_procs -C slapd -c 1:1',
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
'openldap': {
|
||||
'rootpw': repo.vault.password_for(f'{node.name} openldap rootpw'),
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
@metadata_reactor.provides(
|
||||
'icinga2_api/openldap/services/OPENLDAP CERTIFICATE',
|
||||
)
|
||||
def cert_check(metadata):
|
||||
return {
|
||||
'icinga2_api': {
|
||||
'openldap': {
|
||||
'services': {
|
||||
'OPENLDAP CERTIFICATE': {
|
||||
'check_command': 'check_certificate_at',
|
||||
'vars.domain': metadata.get('openldap/my_hostname'),
|
||||
'vars.port': '636',
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
@metadata_reactor.provides(
|
||||
'firewall/port_rules/389',
|
||||
'firewall/port_rules/636',
|
||||
)
|
||||
def sperrfix(metadata):
|
||||
sources = metadata.get('openldap/restrict-to', set())
|
||||
|
||||
return {
|
||||
'firewall': {
|
||||
'port_rules': {
|
||||
'389': atomic(sources),
|
||||
'636': atomic(sources),
|
||||
},
|
||||
},
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue