From 10d264fa3899122a99334e9012057e9ef8ba668d Mon Sep 17 00:00:00 2001 From: Felix Bartels Date: Mon, 4 Mar 2019 20:14:36 +0100 Subject: [PATCH] Add example to run meet standalone (#90) * refactor ssl generation make ssl certificate names match container names add dns names to certificates * add example to run meet and its dependencies together with an existing kopano * update webapp example * remove port numbers from ssl cert as these could have been specified in a demo environment * set default values for HTTP, HTTPS and EMAIL fail if FQDN is unset make smtp and kopano-server ports configurable * add hint about 2015 to setup.sh * also add new defaults to webapp compose * add example for standalone core as well --- docker-compose.yml | 61 +++++++++++---------- examples/core.yml | 107 ++++++++++++++++++++++++++++++++++++ examples/meet-kopano.env | 8 +++ examples/meet-kopano.yml | 113 +++++++++++++++++++++++++++++++++++++++ examples/webapp.yml | 19 +++++-- setup.sh | 8 ++- ssl/start.sh | 43 +++++++++------ 7 files changed, 309 insertions(+), 50 deletions(-) create mode 100644 examples/core.yml create mode 100644 examples/meet-kopano.env create mode 100644 examples/meet-kopano.yml diff --git a/docker-compose.yml b/docker-compose.yml index eb11393..c3aca71 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -2,16 +2,16 @@ version: "3.5" services: web: - image: ${docker_repo:?err}/kopano_web + image: ${docker_repo:-zokradonh}/kopano_web container_name: web restart: always ports: - "2015:2015" - - "${HTTP}:80" - - "${HTTPS}:443" + - "${HTTP:-80}:80" + - "${HTTPS:-443}:443" environment: - - EMAIL=${EMAIL} - - FQDN=${FQDN} + - EMAIL=${EMAIL:-off} + - FQDN=${FQDN?err} command: wrapper.sh cap_drop: - ALL @@ -25,10 +25,10 @@ services: networks: web-net: aliases: - - ${FQDN} + - ${FQDNCLEANED?err} ldap: - image: ${docker_repo:?err}/kopano_ldap_demo + image: ${docker_repo:-zokradonh}/kopano_ldap_demo container_name: ldap ports: - ${LDAPPORT:-389}:389 @@ -109,7 +109,7 @@ services: depends_on: - ldap ports: - - "25:25" + - "${SMTPPORT:-25}:25" - "465:465" - "587:587" volumes: @@ -181,15 +181,18 @@ services: - kopano-net kopano_ssl: - image: ${docker_repo:?err}/kopano_ssl + image: ${docker_repo:-zokradonh}/kopano_ssl container_name: kopano_ssl + environment: + - FQDN=${FQDN} + - PKI_COUNTRY=NL env_file: - kopano_ssl.env volumes: - kopanossl/:/kopano/ssl kopano_server: - image: ${docker_repo:?err}/kopano_core:${CORE_VERSION} + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} hostname: kopano_server container_name: kopano_server depends_on: @@ -197,8 +200,8 @@ services: - ldap - kopano_ssl ports: - - 236:236 - - 237:237 + - ${KOPANOPORT:-236}:236 + - ${KOPANOSPORT:-237}:237 environment: - SERVICE_TO_START=server - TZ=${TZ} @@ -209,7 +212,7 @@ services: - KCCONF_SERVER_MYSQL_DATABASE=${MYSQL_DATABASE} - KCCONF_SERVER_MYSQL_USER=${MYSQL_USER} - KCCONF_SERVER_MYSQL_PASSWORD=${MYSQL_PASSWORD} - - KCCONF_SERVER_SERVER_SSL_KEY_FILE=/kopano/ssl/kserver.pem + - KCCONF_SERVER_SERVER_SSL_KEY_FILE=/kopano/ssl/kopano_server.pem - KCCONF_SERVER_SERVER_SSL_CA_FILE=/kopano/ssl/ca.pem - KCCONF_SERVER_SERVER_NAME=Kopano - KCCONF_SERVER_SSLKEYS_PATH=/kopano/ssl/clients @@ -239,7 +242,7 @@ services: - kopanosocket/:/run/kopano kopano_webapp: - image: ${docker_repo:?err}/kopano_webapp:${WEBAPP_VERSION} + image: ${docker_repo:-zokradonh}/kopano_webapp:${WEBAPP_VERSION:-latest} hostname: kopano_webapp container_name: kopano_webapp volumes: @@ -255,7 +258,7 @@ services: - kopano-net kopano_zpush: - image: ${docker_repo:?err}/kopano_zpush:${ZPUSH_VERSION} + image: ${docker_repo:-zokradonh}/kopano_zpush:${ZPUSH_VERSION:-latest} hostname: kopano_zpush container_name: kopano_zpush volumes: @@ -271,7 +274,7 @@ services: - kopano-net kopano_grapi: - image: ${docker_repo:?err}/kopano_core:${CORE_VERSION} + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} container_name: kopano_grapi volumes: - kopanosocket/:/run/kopano @@ -284,7 +287,7 @@ services: - kopano-net kopano_kapi: - image: ${docker_repo:?err}/kopano_core:${CORE_VERSION} + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} container_name: kopano_kapi depends_on: - kopano_grapi @@ -305,7 +308,7 @@ services: - web-net kopano_dagent: - image: ${docker_repo:?err}/kopano_core:${CORE_VERSION} + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} container_name: kopano_dagent volumes: - kopanossl/:/kopano/ssl @@ -313,15 +316,15 @@ services: environment: - SERVICE_TO_START=dagent - TZ=${TZ} + - KCCONF_DAGENT_SSLKEY_FILE=/kopano/ssl/kopano_dagent.pem - KCCONF_DAGENT_LOG_LEVEL=3 - - KCCONF_DAGENT_SSLKEY_FILE=/kopano/ssl/kdagent.pem env_file: - kopano_dagent.env networks: - kopano-net kopano_spooler: - image: ${docker_repo:?err}/kopano_core:${CORE_VERSION} + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} container_name: kopano_spooler hostname: spooler domainname: ${LDAP_DOMAIN} @@ -333,14 +336,14 @@ services: - TZ=${TZ} - KCCONF_SPOOLER_LOG_LEVEL=3 - KCCONF_SPOOLER_SMTP_SERVER=mail - - KCCONF_SPOOLER_SSLKEY_FILE=/kopano/ssl/kspooler.pem + - KCCONF_SPOOLER_SSLKEY_FILE=/kopano/ssl/kopano_spooler.pem env_file: - kopano_spooler.env networks: - kopano-net kopano_gateway: - image: ${docker_repo:?err}/kopano_core:${CORE_VERSION} + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} container_name: kopano_gateway volumes: - kopanossl/:/kopano/ssl @@ -356,7 +359,7 @@ services: - kopano-net kopano_ical: - image: ${docker_repo:?err}/kopano_core:${CORE_VERSION} + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} container_name: kopano_ical volumes: - kopanossl/:/kopano/ssl @@ -372,7 +375,7 @@ services: - web-net kopano_monitor: - image: ${docker_repo:?err}/kopano_core:${CORE_VERSION} + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} container_name: kopano_monitor volumes: - kopanossl/:/kopano/ssl @@ -386,7 +389,7 @@ services: - kopano-net kopano_search: - image: ${docker_repo:?err}/kopano_core:${CORE_VERSION} + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} container_name: kopano_search volumes: - kopanossl/:/kopano/ssl @@ -401,7 +404,7 @@ services: - kopano-net kopano_konnect: - image: ${docker_repo:?err}/kopano_konnect:${KONNECT_VERSION} + image: ${docker_repo:-zokradonh}/kopano_konnect:${KONNECT_VERSION:-latest} container_name: kopano_konnect command: wrapper.sh volumes: @@ -416,14 +419,14 @@ services: - web-net kopano_playground: - image: ${docker_repo:?err}/kopano_playground + image: ${docker_repo:-zokradonh}/kopano_playground container_name: kopano_playground networks: - kopano-net - web-net kopano_kwmserver: - image: ${docker_repo:?err}/kopano_kwmserver:${KWM_VERSION} + image: ${docker_repo:-zokradonh}/kopano_kwmserver:${KWM_VERSION:-latest} container_name: kopano_kwmserver command: wrapper.sh environment: @@ -437,7 +440,7 @@ services: - web-net kopano_meet: - image: ${docker_repo:?err}/kopano_meet:${MEET_VERSION} + image: ${docker_repo:-zokradonh}/kopano_meet:${MEET_VERSION:-latest} container_name: kopano_meet environment: - SERVICE_TO_START=meet diff --git a/examples/core.yml b/examples/core.yml new file mode 100644 index 0000000..f04d09b --- /dev/null +++ b/examples/core.yml @@ -0,0 +1,107 @@ +version: "3.5" + +services: + ldap: + image: ${docker_repo:-zokradonh}/kopano_ldap_demo + container_name: ldap + ports: + - ${LDAPPORT:-389}:389 + environment: + - LDAP_ORGANISATION=${LDAP_ORGANISATION} + - LDAP_DOMAIN=${LDAP_DOMAIN} + - LDAP_BASE_DN=${LDAP_BASE_DN} + - LDAP_ADMIN_PASSWORD=${LDAP_ADMIN_PASSWORD} + - LDAP_READONLY_USER=true + - LDAP_READONLY_USER_PASSWORD=${LDAP_READONLY_USER_PASSWORD} + command: "--loglevel info --copy-service" + volumes: + - ldap:/var/lib/ldap + - slapd:/etc/ldap/slapd.d + networks: + - ldap-net + + db: + image: mariadb:10.3.10-bionic + restart: always + container_name: kopano_db + volumes: + - mysql/:/var/lib/mysql + environment: + - MYSQL_ROOT_PASSWORD=${MYSQL_ROOT_PASSWORD} + - MYSQL_USER=${MYSQL_USER} + - MYSQL_PASSWORD=${MYSQL_PASSWORD} + - MYSQL_DATABASE=${MYSQL_DATABASE} + healthcheck: + test: ["CMD-SHELL", 'mysql --database=$$MYSQL_DATABASE --password=$$MYSQL_ROOT_PASSWORD --execute="SELECT count(table_name) > 0 FROM information_schema.tables;" --skip-column-names -B'] + interval: 30s + timeout: 10s + retries: 4 + networks: + - kopano-net + + kopano_ssl: + image: ${docker_repo:-zokradonh}/kopano_ssl + container_name: kopano_ssl + environment: + - FQDN=${FQDN} + - PKI_COUNTRY=NL + volumes: + - /etc/kopano/ssl/:/kopano/ssl + + kopano_server: + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} + hostname: kopano_server + container_name: kopano_server + depends_on: + - db + - ldap + - kopano_ssl + ports: + - ${KOPANOPORT:-236}:236 + - ${KOPANOSPORT:-237}:237 + environment: + - SERVICE_TO_START=server + - TZ=${TZ} + - KCCONF_SERVER_COREDUMP_ENABLED=no + - KCCONF_SERVER_LOG_LEVEL=3 + - KCCONF_SERVER_MYSQL_HOST=${MYSQL_HOST} + - KCCONF_SERVER_MYSQL_PORT=3306 + - KCCONF_SERVER_MYSQL_DATABASE=${MYSQL_DATABASE} + - KCCONF_SERVER_MYSQL_USER=${MYSQL_USER} + - KCCONF_SERVER_MYSQL_PASSWORD=${MYSQL_PASSWORD} + - KCCONF_SERVER_SERVER_SSL_KEY_FILE=/kopano/ssl/kopano_server.pem + - KCCONF_SERVER_SERVER_SSL_CA_FILE=/kopano/ssl/ca.pem + - KCCONF_SERVER_SERVER_NAME=Kopano + - KCCONF_SERVER_SSLKEYS_PATH=/kopano/ssl/clients + - KCCONF_SERVER_PROXY_HEADER=* # delete line if webapp is not behind reverse proxy + - KCCONF_SERVER_SYSTEM_EMAIL_ADDRESS=${POSTMASTER_ADDRESS} + - KCCONF_SERVER_SYNC_GAB_REALTIME=no + - KCCONF_LDAP_LDAP_URI=${LDAP_SERVER} + - KCCONF_LDAP_LDAP_BIND_USER=${LDAP_BIND_DN} + - KCCONF_LDAP_LDAP_BIND_PASSWD=${LDAP_BIND_PW} + - KCCONF_LDAP_LDAP_SEARCH_BASE=${LDAP_SEARCH_BASE} + - KCUNCOMMENT_LDAP_1=${KCUNCOMMENT_LDAP_1} + - KCCOMMENT_LDAP_1=${KCCOMMENT_LDAP_1} + - ADDITIONAL_KOPANO_PACKAGES=${ADDITIONAL_KOPANO_PACKAGES} + networks: + - kopano-net + - ldap-net + - web-net + volumes: + - kopanodata/:/kopano/data + - /etc/kopano/ssl/:/kopano/ssl + - /run/kopano/:/run/kopano + +volumes: + ldap: + slapd: + mysql: + kopanodata: + +networks: + web-net: + kopano-net: + driver: bridge + ldap-net: + name: ldap-net + driver: bridge diff --git a/examples/meet-kopano.env b/examples/meet-kopano.env new file mode 100644 index 0000000..00f4ddf --- /dev/null +++ b/examples/meet-kopano.env @@ -0,0 +1,8 @@ +FQDN=kopano.demo:2015 +FQDNCLEANED=kopano-demo +INSECURE=yes +TZ=Europe/Berlin +HTTP=10080 +HTTPS=10443 + +# TODO add reverse proxy example, make sure that requests go through reverse proxy diff --git a/examples/meet-kopano.yml b/examples/meet-kopano.yml new file mode 100644 index 0000000..7381e7f --- /dev/null +++ b/examples/meet-kopano.yml @@ -0,0 +1,113 @@ +version: "3.5" + +services: + web: + image: ${docker_repo:-zokradonh}/kopano_web + container_name: web + restart: always + ports: + - "2015:2015" + - "${HTTP:-80}:80" + - "${HTTPS:-443}:443" + environment: + - EMAIL=${EMAIL:-off} + - FQDN=${FQDN?err} + command: wrapper.sh + cap_drop: + - ALL + cap_add: + - NET_BIND_SERVICE + - CHOWN + - SETGID + - SETUID + volumes: + - web:/.kweb + networks: + web-net: + aliases: + - ${FQDNCLEANED?err} + + kopano_ssl: + image: ${docker_repo:-zokradonh}/kopano_ssl + container_name: kopano_ssl + environment: + - FQDN=${FQDN} + - PKI_COUNTRY=NL + volumes: + - /etc/kopano/ssl/:/kopano/ssl + + kopano_grapi: + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} + container_name: kopano_grapi + volumes: + - /run/kopano:/run/kopano + environment: + - SERVICE_TO_START=grapi + - TZ=${TZ} + networks: + - kopano-net + + kopano_kapi: + image: ${docker_repo:-zokradonh}/kopano_core:${CORE_VERSION:-latest} + container_name: kopano_kapi + depends_on: + - kopano_grapi + volumes: + - /etc/kopano/ssl:/kopano/ssl + - /run/kopano:/run/kopano + environment: + - SERVICE_TO_START=kapid + - TZ=${TZ} + - KCCONF_KAPID_LOG_LEVEL=DEBUG + - KCCONF_KAPID_OIDC_ISSUER_IDENTIFIER=https://${FQDN} + - KCCONF_KAPID_INSECURE=${INSECURE} + networks: + - kopano-net + - web-net + + kopano_konnect: + image: ${docker_repo:-zokradonh}/kopano_konnect:${KONNECT_VERSION:-latest} + container_name: kopano_konnect + command: wrapper.sh + volumes: + - /etc/kopano/ssl:/kopano/ssl + - /run/kopano:/run/kopano + environment: + - FQDN=${FQDN} + networks: + - web-net + + kopano_kwmserver: + image: ${docker_repo:-zokradonh}/kopano_kwmserver:${KWM_VERSION:-latest} + container_name: kopano_kwmserver + command: wrapper.sh + environment: + - INSECURE=${INSECURE} + - oidc_issuer_identifier=https://${FQDN} + volumes: + - /etc/kopano/ssl:/kopano/ssl + networks: + - web-net + + kopano_meet: + image: ${docker_repo:-zokradonh}/kopano_meet:${MEET_VERSION:-latest} + container_name: kopano_meet + environment: + - SERVICE_TO_START=meet + - KCCONF_KWEBD_TLS=no + depends_on: + - kopano_kapi + - kopano_konnect + - kopano_kwmserver + - web + networks: + - web-net + +volumes: + web: + kopanossl: + +networks: + web-net: + kopano-net: + driver: bridge diff --git a/examples/webapp.yml b/examples/webapp.yml index cf79dbf..ab14ec7 100644 --- a/examples/webapp.yml +++ b/examples/webapp.yml @@ -2,24 +2,33 @@ version: "3.5" services: web: - image: ${docker_repo:?err}/kopano_web + image: ${docker_repo:-zokradonh}/kopano_web container_name: web restart: always ports: - "2015:2015" - - "${HTTP}:8080" - - "${HTTPS}:8443" + - "${HTTP}:80" + - "${HTTPS}:443" environment: - EMAIL=${EMAIL} - FQDN=${FQDN} command: wrapper.sh + cap_drop: + - ALL + cap_add: + - NET_BIND_SERVICE + - CHOWN + - SETGID + - SETUID volumes: - web:/.kweb networks: - - web-net + web-net: + aliases: + - ${FQDN} kopano_webapp: - image: ${docker_repo:?err}/kopano_webapp:${WEBAPP_VERSION} + image: ${docker_repo:-zokradonh}/kopano_webapp:${WEBAPP_VERSION:-latest} hostname: kopano_webapp container_name: kopano_webapp volumes: diff --git a/setup.sh b/setup.sh index d288ff9..acb39d8 100755 --- a/setup.sh +++ b/setup.sh @@ -114,7 +114,9 @@ if [ ! -e ./.env ]; then LDAP_ORGANISATION=${new_value:-$value_default} value_default="kopano.demo" - read -p "FQDN to be used (for reverse proxy) [$value_default]: " new_value + read -p "FQDN to be used (for reverse proxy). + Tipp: use port 2015 in case port 443 is already in use on the system. + [$value_default]: " new_value FQDN=${new_value:-$value_default} value_default="self_signed" @@ -307,10 +309,14 @@ TZ=$TZ # Defines how Kopano can be accessed from the outside world FQDN=$FQDN +FQDNCLEANED=${FQDN%:*} EMAIL=$EMAIL HTTP=80 HTTPS=443 LDAPPORT=389 +SMTPPORT=25 +KOPANOPORT=236 +KOPANOSPORT=237 # Settings for test environments INSECURE=$INSECURE diff --git a/ssl/start.sh b/ssl/start.sh index 1a9055c..d38e761 100755 --- a/ssl/start.sh +++ b/ssl/start.sh @@ -2,28 +2,37 @@ mkdir -p /kopano/ssl/clients/ +set -euo pipefail +IFS=$'\n\t' + +# clean out any potential port numbers +FQDN=${FQDN%:*} + if [ ! -f /kopano/ssl/ca.pem ]; then # https://github.com/google/easypki - echo "Creating CA and server certificates..." + echo "Creating CA certificate..." easypki create --filename internalca --organizational-unit primary --expire 3650 --ca "Internal Kopano System" - for s in kserver kdagent kmonitor ksearch kspooler kwebapp; do - easypki create --ca-name internalca --organizational-unit $s --expire 3650 $s - cp /kopano/easypki/internalca/keys/$s.key /kopano/ssl/$s.pem.tmp - cat /kopano/easypki/internalca/certs/$s.crt >> /kopano/ssl/$s.pem.tmp - openssl x509 -in /kopano/easypki/internalca/certs/$s.crt -pubkey -noout > /kopano/ssl/clients/$s-public.pem.tmp - mv /kopano/ssl/$s.pem.tmp /kopano/ssl/$s.pem - mv /kopano/ssl/clients/$s-public.pem.tmp /kopano/ssl/clients/$s-public.pem - done - cp /kopano/easypki/internalca/certs/internalca.crt /kopano/ssl/ca.pem.tmp mv /kopano/ssl/ca.pem.tmp /kopano/ssl/ca.pem + + for s in kopano_server kopano_dagent kopano_monitor kopano_search kopano_spooler kopano_webapp; do + if [ ! -f /kopano/ssl/$s.pem ]; then + echo "Creating $s certificate..." + easypki create --ca-name internalca --organizational-unit $s --expire 3650 --dns $s --dns $FQDN $s + cp /kopano/easypki/internalca/keys/$s.key /kopano/ssl/$s.pem.tmp + cat /kopano/easypki/internalca/certs/$s.crt >> /kopano/ssl/$s.pem.tmp + openssl x509 -in /kopano/easypki/internalca/certs/$s.crt -pubkey -noout > /kopano/ssl/clients/$s-public.pem.tmp + mv /kopano/ssl/$s.pem.tmp /kopano/ssl/$s.pem + mv /kopano/ssl/clients/$s-public.pem.tmp /kopano/ssl/clients/$s-public.pem + fi + done fi # Konnect - create encryption key if not already present enckey="/kopano/ssl/konnectd-encryption.key" if [ ! -f $enckey ]; then - echo "creating new encryption key" + echo "Creating Konnect encryption key..." openssl rand -out $enckey.tmp 32 mv $enckey.tmp $enckey fi @@ -31,8 +40,8 @@ fi # Konnect - create token signing key if not already present signkey="/kopano/ssl/konnectd-tokens-signing-key.pem" if [ ! -f $signkey ]; then - echo "creating new token signing key" - openssl genpkey -algorithm RSA -out $signkey.tmp -pkeyopt rsa_keygen_bits:4096 + echo "Creating Konnect token signing key..." + openssl genpkey -algorithm RSA -out $signkey.tmp -pkeyopt rsa_keygen_bits:4096 2&> /dev/null chmod go+r $signkey.tmp mv $signkey.tmp $signkey fi @@ -40,9 +49,13 @@ fi # Kapi secretkey="/kopano/ssl/kapid-pubs-secret.key" if [ ! -f $secretkey ]; then + echo "Creating Kapi secret key..." openssl rand -out $secretkey.tmp -hex 64 mv $secretkey.tmp $secretkey fi -ls -l /kopano/ssl/*.pem -ls -l /kopano/ssl/*.key +echo "SSL certs:" +ls -l /kopano/ssl/*.* + +echo "Client public keys:" +ls -l /kopano/ssl/clients/*