summary refs log tree commit diff
path: root/contrib/docker
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/docker')
-rw-r--r--contrib/docker/README.md70
-rw-r--r--contrib/docker/conf/homeserver.yaml190
-rw-r--r--contrib/docker/conf/log.config36
-rw-r--r--contrib/docker/docker-compose.yml37
-rw-r--r--contrib/docker/rob/docker-compose.yaml39
-rwxr-xr-xcontrib/docker/rob/rootfs/etc/service/synapse/finish17
-rwxr-xr-xcontrib/docker/rob/rootfs/etc/service/synapse/run75
-rwxr-xr-xcontrib/docker/start.py38
8 files changed, 502 insertions, 0 deletions
diff --git a/contrib/docker/README.md b/contrib/docker/README.md
new file mode 100644
index 0000000000..c15517d0e0
--- /dev/null
+++ b/contrib/docker/README.md
@@ -0,0 +1,70 @@
+# Synapse Docker
+
+## Build
+
+Build the docker image with the `docker build` command from the root of the synapse repository.
+
+```
+docker build -t matrixdotorg/synapse:v0.22.1 .
+```
+
+The `-t` option sets the image tag. Official images are tagged `matrixdotorg/synapse:<version>` where `<version>` is the same as the release tag in the synapse git repository.
+
+## Configure
+
+Synapse provides a command for generating homeserver configuration files. These are a good starting point for setting up your own deployment.
+
+The documentation below will refer to a `CONFIG_PATH` shell variable. This is a path to a directory where synapse configuration will be stored. It needs to be mapped into the container as a volume at `/synapse/config/` as can be seen in the example `docker run` command.
+
+Docker container environment variables:
+* `GENERATE_CONFIG` - Set this to any non-empty string, such as `yes`, to trigger generation of configuration files. Existing files in the `CONFIG_PATH` will **not** be overwritten.
+* `POSTGRES_DATABASE` - The database name for the synapse postgres database. [default: `synapse`]
+* `POSTGRES_HOST` - The host of the postgres database if you wish to use postgresql instead of sqlite3. [default: `postgres` which is useful when using a container on the same docker network in a compose file where the postgres service is called `postgres`] **NOTE**: `localhost` and `127.0.0.1` refer to the container itself unless running the container with `host` networking.
+* `POSTGRES_PASSWORD` - The password for the synapse postgres database. **If this is set then postgres will be used instead of sqlite3.** [default: none] **NOTE**: You are highly encouraged to use postgresql! Please use the compose file to make it easier to deploy.
+* `POSTGRES_USER` - The user for the synapse postgres database. [default: `postgres`]
+* `REPORT_STATS` - Whether to send anonymous usage statistics back to the Matrix project which helps us to get funding! Must be `yes` or `no`. [default: `yes`]
+* `SERVER_NAME` - The domain used for the Matrix homeserver. If you intend to run this synapse instance on a public domain, use that domain. [default: `localhost`]
+
+```
+CONFIG_PATH=/my/magical/config/path/
+mkdir -p ${CONFIG_PATH}
+docker run \
+    --rm \
+    -e GENERATE_CONFIG=yes \
+    -e POSTGRES_PASSWORD=MyVerySecretPassword \
+    -e REPORT_STATS=yes \
+    -e SERVER_NAME=example.com \
+    -v ${CONFIG_PATH}:/synapse/config/ \
+    matrixdotorg/synapse:v0.22.1
+```
+
+This will create a temporary container from the image and use the synapse code for generating configuration files and TLS keys and certificates for the specified `SERVER_NAME` domain. The files are written to `CONFIG_PATH`.
+
+## Run
+
+**NOTE**: If you are not using postgresql and are using sqlite3 as your database, you will need to make a directory to store the sqlite3 database file in and then mount this volume into the container at `/synapse/data/`. As it is so easy to use postgresql, when using Docker containers, this is not documented to somewhat discourage it. Choose a `POSTGRES_PASSWORD` instead.
+
+### Docker Compose
+
+A `docker-compose.yaml` file is included to ease deployment of the basic synapse and postgres setup. Remember to set a `POSTGRES_PASSWORD` when generating your configuration above. You will need it for running the containers in the composition.
+
+From the `docker/` subdirectory of the synapse repository:
+```
+CONFIG_PATH=/my/magical/config/path/
+POSTGRES_PASSWORD=MyVerySecretPassword \
+docker-compose \
+    -p synapse \
+    up -d
+```
+
+### Docker
+
+Note that the following is just a guideline and you may need to add parameters to the docker run command to account for the network situation with your postgres database.
+
+```
+docker run \
+    -d \
+    --name synapse \
+    -v ${CONFIG_PATH}:/synapse/config/ \
+    matrixdotorg/synapse:v0.22.1
+```
diff --git a/contrib/docker/conf/homeserver.yaml b/contrib/docker/conf/homeserver.yaml
new file mode 100644
index 0000000000..7450cc1228
--- /dev/null
+++ b/contrib/docker/conf/homeserver.yaml
@@ -0,0 +1,190 @@
+# vim:ft=yaml
+
+## TLS ##
+
+tls_certificate_path: "/data/{{ SYNAPSE_SERVER_NAME }}.tls.crt"
+tls_private_key_path: "/data/{{ SYNAPSE_SERVER_NAME }}.tls.key"
+tls_dh_params_path: "/data/{{ SYNAPSE_SERVER_NAME }}.tls.dh"
+no_tls: {{ "True" if SYNAPSE_NO_TLS else "False" }}
+tls_fingerprints: []
+
+## Server ##
+
+server_name: "{{ SYNAPSE_SERVER_NAME }}"
+pid_file: /homeserver.pid
+web_client: {{ "True" if SYNAPSE_WEB_CLIENT else "False" }}
+soft_file_limit: 0
+
+## Ports ##
+
+listeners:
+  {% if not SYNAPSE_NO_TLS %}
+  -
+    port: 8448
+    bind_addresses: ['0.0.0.0']
+    type: http
+    tls: true
+    x_forwarded: false
+    resources:
+      - names: [client, webclient]
+        compress: true
+      - names: [federation]  # Federation APIs
+        compress: false
+  {% endif %}
+
+  - port: 8008
+    tls: false
+    bind_addresses: ['0.0.0.0']
+    type: http
+    x_forwarded: false
+
+    resources:
+      - names: [client, webclient]
+        compress: true
+      - names: [federation]
+        compress: false
+
+## Database ##
+
+{% if POSTGRES_PASSWORD %}
+database:
+  name: "psycopg2"
+  args:
+    user: "{{ POSTGRES_USER or "matrix" }}"
+    password: "{{ POSTGRES_PASSWORD }}"
+    database: "{{ POSTGRES_DB or "matrix" }}"
+    host: "{{ POSTGRES_HOST or "db" }}"
+    port: "{{ POSTGRES_PORT or "5432" }}"
+    cp_min: 5
+    cp_max: 10
+{% else %}
+database:
+  name: "sqlite3"
+  args:
+    database: "/data/homeserver.db"
+{% endif %}
+
+## Performance ##
+
+event_cache_size: "{{ SYNAPSE_EVENT_CACHE_SIZE or "10K" }}"
+verbose: 0
+log_file: "/data/homeserver.log"
+log_config: "/data/{{ SYNAPSE_SERVER_NAME }}.log.config"
+
+## Ratelimiting ##
+
+rc_messages_per_second: 0.2
+rc_message_burst_count: 10.0
+federation_rc_window_size: 1000
+federation_rc_sleep_limit: 10
+federation_rc_sleep_delay: 500
+federation_rc_reject_limit: 50
+federation_rc_concurrent: 3
+
+## Files ##
+
+media_store_path: "/data/media"
+uploads_path: "/data/uploads"
+max_upload_size: "10M"
+max_image_pixels: "32M"
+dynamic_thumbnails: false
+
+# List of thumbnail to precalculate when an image is uploaded.
+thumbnail_sizes:
+- width: 32
+  height: 32
+  method: crop
+- width: 96
+  height: 96
+  method: crop
+- width: 320
+  height: 240
+  method: scale
+- width: 640
+  height: 480
+  method: scale
+- width: 800
+  height: 600
+  method: scale
+
+url_preview_enabled: False
+max_spider_size: "10M"
+
+## Captcha ##
+
+recaptcha_public_key: "YOUR_PUBLIC_KEY"
+recaptcha_private_key: "YOUR_PRIVATE_KEY"
+enable_registration_captcha: False
+recaptcha_siteverify_api: "https://www.google.com/recaptcha/api/siteverify"
+
+## Turn ##
+
+turn_uris: []
+turn_shared_secret: "YOUR_SHARED_SECRET"
+turn_user_lifetime: "1h"
+turn_allow_guests: True
+
+## Registration ##
+
+enable_registration: {{ "True" if SYNAPSE_ENABLE_REGISTRATION else "False" }}
+registration_shared_secret: "{{ SYNAPSE_REGISTRATION_SHARED_SECRET }}"
+bcrypt_rounds: 12
+allow_guest_access: {{ "True" if SYNAPSE_ALLOW_GUEST else "False" }}
+
+# The list of identity servers trusted to verify third party
+# identifiers by this server.
+trusted_third_party_id_servers:
+    - matrix.org
+    - vector.im
+    - riot.im
+
+## Metrics ###
+
+enable_metrics: False
+report_stats: False
+
+## API Configuration ##
+
+room_invite_state_types:
+    - "m.room.join_rules"
+    - "m.room.canonical_alias"
+    - "m.room.avatar"
+    - "m.room.name"
+
+app_service_config_files: []
+macaroon_secret_key: "{{ SYNAPSE_MACAROON_SECRET_KEY }}"
+expire_access_token: False
+
+## Signing Keys ##
+
+signing_key_path: "/data/{{ SYNAPSE_SERVER_NAME }}.signing.key"
+old_signing_keys: {}
+key_refresh_interval: "1d" # 1 Day.
+
+# The trusted servers to download signing keys from.
+perspectives:
+  servers:
+    "matrix.org":
+      verify_keys:
+        "ed25519:auto":
+          key: "Noi6WqcDj0QmPxCNQqgezwTlBKrfqehY1u2FyWP9uYw"
+
+password_config:
+   enabled: true
+
+#email:
+#   enable_notifs: false
+#   smtp_host: "localhost"
+#   smtp_port: 25
+#   smtp_user: "exampleusername"
+#   smtp_pass: "examplepassword"
+#   require_transport_security: False
+#   notif_from: "Your Friendly %(app)s Home Server <noreply@example.com>"
+#   app_name: Matrix
+#   template_dir: res/templates
+#   notif_template_html: notif_mail.html
+#   notif_template_text: notif_mail.txt
+#   notif_for_new_users: True
+#   riot_base_url: "http://localhost/riot"
+
+enable_group_creation: true
diff --git a/contrib/docker/conf/log.config b/contrib/docker/conf/log.config
new file mode 100644
index 0000000000..45e7eef953
--- /dev/null
+++ b/contrib/docker/conf/log.config
@@ -0,0 +1,36 @@
+version: 1
+
+formatters:
+  precise:
+   format: '%(asctime)s - %(name)s - %(lineno)d - %(levelname)s - %(request)s- %(message)s'
+
+filters:
+  context:
+    (): synapse.util.logcontext.LoggingContextFilter
+    request: ""
+
+handlers:
+  file:
+    class: logging.handlers.RotatingFileHandler
+    formatter: precise
+    filename: /data/homeserver.log
+    maxBytes: 104857600
+    backupCount: 10
+    filters: [context]
+  console:
+    class: logging.StreamHandler
+    formatter: precise
+    filters: [context]
+
+loggers:
+    synapse:
+        level: INFO
+
+    synapse.storage.SQL:
+        # beware: increasing this to DEBUG will make synapse log sensitive
+        # information such as access tokens.
+        level: INFO
+
+root:
+    level: INFO
+    handlers: [file, console]
diff --git a/contrib/docker/docker-compose.yml b/contrib/docker/docker-compose.yml
new file mode 100644
index 0000000000..b8f9741f05
--- /dev/null
+++ b/contrib/docker/docker-compose.yml
@@ -0,0 +1,37 @@
+# This compose file is compatible with Copose itself, it might need some
+# adjustments to run properly with stack.
+
+version: '3'
+
+services:
+
+  synapse:
+    image: synapse
+    # Since snyapse does not retry to connect to the database, restart upon
+    # failure
+    restart: unless-stopped
+    # See the readme for a full documentation of the environment settings
+    environment:
+      - SYNAPSE_SERVER_NAME=my.matrix.host
+      - SYNAPSE_ENABLE_REGISTRATION=yes
+    volumes:
+      - ./files:/data
+    depends_on:
+      - db
+    # One may either expose ports directly
+    ports:
+      - 8448:8448/tcp
+    # ... or use a reverse proxy, here is an example for traefik
+    labels:
+      - traefik.enable=true
+      - traefik.frontend.rule=Host:my.matrix.Host
+      - traefik.port=8448
+
+  db:
+    image: postgres:latest
+    # Change that password, of course!
+    environment:
+      - POSTGRES_USER=matrix
+      - POSTGRES_PASSWORD=changeme
+    volumes:
+      - ./schemas:/var/lib/postgresql/data
diff --git a/contrib/docker/rob/docker-compose.yaml b/contrib/docker/rob/docker-compose.yaml
new file mode 100644
index 0000000000..73cc29f8fd
--- /dev/null
+++ b/contrib/docker/rob/docker-compose.yaml
@@ -0,0 +1,39 @@
+# Copyright 2017 Vector Creations Ltd
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+#     http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+version: '3'
+
+services:
+    postgres:
+        image: postgres:9.6.5-alpine
+        environment:
+            POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}
+            POSTGRES_DB: synapse
+        expose:
+            - 5432
+        restart: unless-stopped
+        volumes:
+            - postgres-data:/var/lib/postgresql/data/
+
+    synapse:
+        image: matrixdotorg/synapse:v0.22.1
+        ports:
+            - 8008:8008
+            - 8448:8448
+        restart: unless-stopped
+        volumes:
+            - ${CONFIG_PATH}:/synapse/config/
+
+volumes:
+    postgres-data:
diff --git a/contrib/docker/rob/rootfs/etc/service/synapse/finish b/contrib/docker/rob/rootfs/etc/service/synapse/finish
new file mode 100755
index 0000000000..2aace581a1
--- /dev/null
+++ b/contrib/docker/rob/rootfs/etc/service/synapse/finish
@@ -0,0 +1,17 @@
+#!/bin/bash
+#
+# Copyright 2017 Vector Creations Ltd
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+#     http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+kill -TERM 1
diff --git a/contrib/docker/rob/rootfs/etc/service/synapse/run b/contrib/docker/rob/rootfs/etc/service/synapse/run
new file mode 100755
index 0000000000..dd797d3ef9
--- /dev/null
+++ b/contrib/docker/rob/rootfs/etc/service/synapse/run
@@ -0,0 +1,75 @@
+#!/bin/bash
+#
+# Copyright 2017 Vector Creations Ltd
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+#     http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+set -e
+
+: ${CONFIG_PATH:="/synapse/config"}
+: ${POSTGRES_DATABASE:="synapse"}
+: ${POSTGRES_HOST:="postgres"}
+: ${POSTGRES_USER:="postgres"}
+: ${REPORT_STATS:="yes"}
+: ${SERVER_NAME:="localhost"}
+
+DATABASE_CONFIG_PATH="${CONFIG_PATH}/database.yaml"
+HOMESERVER_CONFIG_PATH="${CONFIG_PATH}/homeserver.yaml"
+SYNAPSE_COMMAND="python -m synapse.app.homeserver"
+
+. /synapse/bin/activate
+cd /synapse
+
+if [[ -n "${GENERATE_CONFIG}" ]]; then
+    ${SYNAPSE_COMMAND} \
+        --server-name ${SERVER_NAME} \
+        --config-path ${HOMESERVER_CONFIG_PATH} \
+        --generate-config \
+        --report-stats=${REPORT_STATS}
+
+    if [[ -f "${DATABASE_CONFIG_PATH}" ]]; then
+        echo "Config file '${DATABASE_CONFIG_PATH}' already exists. Remove it if you want it to be generated."
+    else
+        echo "Generating ${DATABASE_CONFIG_PATH}..."
+        if [[ -n "${POSTGRES_PASSWORD}" ]]; then
+            (cat > ${DATABASE_CONFIG_PATH}) <<EOF
+database:
+  name: psycopg2
+  args:
+    host: ${POSTGRES_HOST}
+    user: ${POSTGRES_USER}
+    password: ${POSTGRES_PASSWORD}
+    database: ${POSTGRES_DATABASE}
+    cp_min: 5
+    cp_max: 10
+EOF
+        else
+            (cat > ${DATABASE_CONFIG_PATH}) <<EOF
+database:
+  name: "sqlite3"
+  args:
+    database: "/synapse/data/homeserver.db"
+EOF
+        fi
+        cat ${DATABASE_CONFIG_PATH} | grep -v password
+    fi
+
+    exit 0
+fi
+
+COMMAND="${SYNAPSE_COMMAND} --config-path ${HOMESERVER_CONFIG_PATH}"
+if [[ -r "${DATABASE_CONFIG_PATH}" ]]; then
+    COMMAND="${COMMAND} --config-path ${DATABASE_CONFIG_PATH}"
+fi
+
+exec ${COMMAND}
diff --git a/contrib/docker/start.py b/contrib/docker/start.py
new file mode 100755
index 0000000000..7057f85f61
--- /dev/null
+++ b/contrib/docker/start.py
@@ -0,0 +1,38 @@
+#!/usr/local/bin/python
+
+import jinja2
+import os
+import sys
+import subprocess
+
+convert = lambda src, dst, environ: open(dst, "w").write(jinja2.Template(open(src).read()).render(**environ))
+mode = sys.argv[1] if len(sys.argv) > 1 else None
+environ = os.environ.copy()
+
+if "SYNAPSE_SERVER_NAME" not in environ:
+    print("Environment variable SYNAPSE_SERVER_NAME is mandatory, exiting.")
+    sys.exit(2)
+
+args = ["python", "-m", "synapse.app.homeserver",
+        "--server-name", os.environ.get("SYNAPSE_SERVER_NAME"),
+        "--report-stats", os.environ.get("SYNAPSE_REPORT_STATS", "no"),
+        "--config-path", os.environ.get("SYNAPSE_CONFIG_PATH", "/compiled/homeserver.yaml")]
+
+# Generate any missing shared secret
+for secret in ("SYNAPSE_REGISTRATION_SHARED_SECRET", "SYNAPSE_MACAROON_SECRET_KEY"):
+    if secret not in environ:
+        print("Generating a random secret for {}".format(secret))
+        environ[secret] = os.urandom(32).encode("hex")
+
+# Parse the configuration file
+if not os.path.exists("/compiled"): os.mkdir("/compiled")
+convert("/conf/homeserver.yaml", "/compiled/homeserver.yaml", environ)
+convert("/conf/log.config", "/compiled/%s.log.config" % environ.get("SYNAPSE_SERVER_NAME"), environ)
+
+# In generate mode, generate a configuration, missing keys, then exit
+if mode == "generate":
+    os.execv("/usr/local/bin/python", args + ["--generate-config"])
+# In normal mode, generate missing keys if any, then run synapse
+else:
+    subprocess.check_output(args + ["--generate-keys"])
+    os.execv("/usr/local/bin/python", args)