Skip to content
This repository has been archived by the owner on Apr 26, 2024. It is now read-only.

Add a Dockerfile for synapse #2846

Merged
merged 52 commits into from
May 11, 2018
Merged
Show file tree
Hide file tree
Changes from 23 commits
Commits
Show all changes
52 commits
Select commit Hold shift + click to select a range
95e02b8
docker: Initial Dockerfile and docker-compose.yaml
superdump Sep 28, 2017
24d1628
docker: s/matrix-org/matrixdotorg/g
superdump Sep 29, 2017
431476f
Initial commit including a Dockerfile for synapse
kaiyou Feb 3, 2018
d434ae3
Add template config files for the Docker image
kaiyou Feb 3, 2018
48bc22f
Allow for a wheel cache and include missing files in the build
kaiyou Feb 4, 2018
6d1e28a
Generate any missing keys before starting synapse
kaiyou Feb 4, 2018
f2bf0cd
Generate shared secrets if not defined in the environment
kaiyou Feb 4, 2018
886c2d5
Support an external postgresql config in the Docker image
kaiyou Feb 4, 2018
042757f
Install the postgres dependencies
kaiyou Feb 4, 2018
1ba2fe1
Provide an example docker compose file
kaiyou Feb 4, 2018
a207ccc
Reuse environment variables of the postgres container
kaiyou Feb 4, 2018
5396533
Merge remote-tracking branch 'origin/rob/docker' into feat-dockerfile
kaiyou Feb 4, 2018
84a9209
Remove etc/service files from rob's branch
kaiyou Feb 4, 2018
9a87b8a
Update sumperdump Docker readme to match this image properties
kaiyou Feb 4, 2018
b8ab78b
Add the build cache/ folder to gitignore
kaiyou Feb 4, 2018
f72c9c1
Fix multiple typos
kaiyou Feb 4, 2018
e9021e1
Run the server as an unprivileged user
kaiyou Feb 4, 2018
8db84e9
Remove docker related files from the python manifest
kaiyou Feb 5, 2018
81010a1
Add dynamic recaptcha configuration in the Docker image
kaiyou Feb 5, 2018
cd51931
Add dynamic TURN configuration in the Docker image
kaiyou Feb 5, 2018
cf4ef60
Document the cache factor environment variable for Docker
kaiyou Feb 5, 2018
d8c7da5
Fix a typo in the Docker README
kaiyou Feb 5, 2018
f5364b4
Point to the 'latest' tag in the Docker documentation
kaiyou Feb 5, 2018
630573a
Do not copy documentation files to the Docker root folder
kaiyou Feb 5, 2018
ee3b160
Only generate configuration files when necessary
kaiyou Feb 5, 2018
107a5c9
Add the non-tls port to the expose list
kaiyou Feb 5, 2018
1ffd9cb
Support loading application service files from /data/appservices/
kaiyou Feb 5, 2018
63fd148
Make it clear that two modes are avaiable in the documentation, impro…
kaiyou Feb 8, 2018
58df3a8
Add some documentation about high performance storage
kaiyou Feb 8, 2018
084afbb
Rename the permissions variable to avoid confusion
kaiyou Feb 8, 2018
b8a4dce
Refactor the start script to better handle mandatory parameters
kaiyou Feb 8, 2018
e174c46
Use 'synapse' as a default postgres user in Docker examples
kaiyou Feb 8, 2018
914a59c
Disable the Web client in the Docker image
kaiyou Feb 8, 2018
a0af005
Honor the SYNAPSE_REPORT_STATS parameter in the Docker image
kaiyou Feb 8, 2018
ef1f8d4
Enable email server configuration from environment variables
kaiyou Feb 8, 2018
b9b668e
Update to Alpine 3.7 and switch to libressl
kaiyou Feb 8, 2018
d8680c9
Make it clear that the image has two modes of operation
kaiyou Feb 8, 2018
48e2c64
Specify the Docker registry in the build tag
kaiyou Feb 8, 2018
a03c382
Specify the Docker registry for the postgres image
kaiyou Feb 8, 2018
e511979
Make SYNAPSE_MACAROON_SECRET_KEY a mandatory option
kaiyou Feb 8, 2018
ca70148
Fix the path to the log config file
kaiyou Feb 8, 2018
6f0b1f8
Generate macaroon and registration secrets, then store the results to…
kaiyou Feb 9, 2018
b815aa0
Remove an accidentally committed test configuration
kaiyou Feb 10, 2018
07f1b71
Explicitely provide the postgres password to synapse in the Compose e…
kaiyou Feb 10, 2018
f44b7c0
Disable logging to file and rely on the console when using Docker
kaiyou Feb 10, 2018
757f1b5
Merge remote-tracking branch 'upstream/master' into feat-dockerfile
kaiyou Mar 17, 2018
a13b786
Merge remote-tracking branch 'upstream/master' into feat-dockerfile
kaiyou Apr 8, 2018
041b41a
Merge remote-tracking branch 'upstream/master' into feat-dockerfile
kaiyou Apr 14, 2018
d4c14e1
Fix the documentation about 'POSTGRES_DB'
kaiyou May 1, 2018
4f2e898
Make the logging level configurable
kaiyou May 1, 2018
9a779c2
Merge remote-tracking branch 'upstream/master' into feat-dockerfile
kaiyou May 2, 2018
5addeaa
Add Docker packaging in the author list
kaiyou May 4, 2018
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .dockerignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
Dockerfile
.travis.yml
.gitignore
demo/etc
tox.ini
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This line seems out of place

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You mean tox.ini, tests are not run in the Docker image. I guess we could include the tox configuration of course, but I did not find it useful.

Copy link

@dali99 dali99 Feb 19, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Alright then, makes sense

1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ demo/media_store.*
demo/etc

uploads
cache

.idea/
media_store/
Expand Down
19 changes: 19 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
FROM python:2-alpine
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Wouldn't it make more sense to base this on docker.io/alpine:3.7? docker.io/python:2-alpine is based on docker.io/alpine:3.4 doesn't receive non-security updates (bug fixes etc) anymore, which means we are potentially stuck on old versions of dependencies.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Disagreeing: I would care a lot more about having an updated Python than updated system libs as long as security patches are backported. docker.io/python:2-alpine is based on the latest Python release deployed separately from apk, as opposed to using the Alpine base image.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The people over at alpine are pretty fast at updating, and at the moment the versions of python in both images are the same. Looking over the python images again, a compromise might be docker.io/python:2-alpine3.7, which is basically the same image as docker.io/python:2-alpine, but is based on a 3.7. I am not sure why they don't default to that though, it doesn't really make sense to me.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, that sounds better, thanks!


RUN apk add --no-cache --virtual .nacl_deps su-exec build-base libffi-dev zlib-dev openssl-dev libjpeg-turbo-dev linux-headers postgresql-dev

COPY . /synapse

# A wheel cache may be provided in ./cache for faster build
RUN cd /synapse \
&& pip install --upgrade pip setuptools psycopg2 \
&& mkdir -p /synapse/cache \
&& pip install -f /synapse/cache --upgrade --process-dependency-links . \
&& mv /synapse/contrib/docker/* / \
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It seems strange to me to litter / with so many files. Why not just keep them all there?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I usually prefer to keep short and simple path for files in Docker images, like /start.py and /conf. But you are right, other files should not be copied.

&& rm -rf setup.py setup.cfg synapse

VOLUME ["/data"]

EXPOSE 8448
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should also EXPOSE 8008


ENTRYPOINT ["/start.py"]
2 changes: 2 additions & 0 deletions MANIFEST.in
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@ recursive-include synapse/static *.js
exclude jenkins.sh
exclude jenkins*.sh
exclude jenkins*
exclude Dockerfile
exclude .dockerignore
recursive-exclude jenkins *.sh

prune .github
Expand Down
109 changes: 109 additions & 0 deletions contrib/docker/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,109 @@
# Synapse Docker

This Docker image will run Synapse as a single process. It does not provide any
database server or TURN server that you should run separately.

If you run a Postgres server, you should simply have it in the same Compose
project or set the proper environment variables and the image will automatically
use that server.

## 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.

You may have a local Python wheel cache available, in which case copy the relevant packages in the ``cache/`` directory at the root of the project.

## Run

It is recommended that you use Docker Compose to run your containers, including
this image and a Postgres server. A sample ``docker-compose.yml`` is provided,
including example labels for reverse proxying and other artifacts.

Then, to run the server:

```
docker-compose up -d
```

In the case you specified a custom path for you configuration file and wish to
generate a fresh ``homeserver.yaml``, simply run:

```
docker-compose run --rm synapse generate
```

If you do not wish to use Compose, you may still run this image using plain
Docker commands. 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 ${DATA_PATH}:/data \
-e SYNAPSE_SERVER_NAME=my.matrix.host \
matrixdotorg/synapse:latest
```


## Volumes

The image expects a single volume, located at ``/data``, that will hold:

* temporary files during uploads;
* uploaded media and thumbnails;
* the SQLite database if you do not configure postgres.

## Environment

Unless you specify a custom path for the configuration file, a very generic
file will be generated, based on the following environment settings.
These are a good starting point for setting up your own deployment.

Global settings:

* ``UID``, the user id Synapse will run as [default 991]
* ``GID``, the group id Synapse will run as [default 991]

Synapse specific settings:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

An environment variable for the cache factor would be neat, although most people aren't going to need it.

Copy link
Contributor Author

@kaiyou kaiyou Feb 5, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The environment variable SYNAPSE_CACHE_FACTOR is supported by default if passed to the container. Just added some documentation about it.


* ``SYNAPSE_SERVER_NAME`` (mandatory), the current server public hostname.
* ``SYNAPSE_CONFIG_PATH``, path to a custom config file (will ignore all
other options then).
* ``SYNAPSE_NO_TLS``, set this variable to disable TLS in Synapse (use this if
you run your own TLS-capable reverse proxy).
* ``SYNAPSE_WEB_CLIENT``, set this variable to enable the embedded Web client.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm strongly against making this possible without manually fiddling in the config. The webclient is deprecated.

* ``SYNAPSE_ENABLE_REGISTRATION``, set this variable to enable registration on
the Synapse instance.
* ``SYNAPSE_ALLOW_GUEST``, set this variable to allow guest joining this server.
* ``SYNAPSE_EVENT_CACHE_SIZE``, the event cache size [default `10K`].
* ``SYNAPSE_CACHE_FACTOR``, the cache factor [default `0.5`].
* ``SYNAPSE_REPORT_STATS``, set this variable to `yes` to enable anonymous
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd default to yes instead.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Defaulting to yes honestly feels like an argument waiting to happen. I'd somewhat recommend it be a required variable with no default.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed with @turt2live, will make it a required argument

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is fine too. I just feel like if it defaults to no, nearly no one will activate it.

statistics reporting back to the Matrix project which helps us to get funding.
* ``SYNAPSE_RECAPTCHA_PUBLIC_KEY``, set this variable to the recaptcha public
key in order to enable recaptcha upon registration.
* ``SYNAPSE_RECAPTCHA_PRIVATE_KEY``, set this variable to the recaptcha private
key in order to enable recaptcha upon registration.
* ``SYNAPSE_TURN_URIS``, set this variable to the coma-separated list of TURN
uris to enable TURN for this homeserver.
* ``SYNAPSE_TURN_SECRET``, set this to the TURN shared secret if required.

Shared secrets, these will be initialized to random values if not set:

* ``SYNAPSE_REGISTRATION_SHARED_SECRET``, secret for registrering users if
registration is disable.
* ``SYNAPSE_MACAROON_SECRET_KEY``, secret for Macaroon.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we really need the SYNAPSE prefix for all of those? Where env is shared across multiple applications, to avoid collisions, sure, but in this container we won't have any other applications.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd gladly add a Riot container to the Compose project later, which might (and probably will) have conflicting environment variables, won't it?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

AFAIK this doesn't really matter, because in docker-compose, environment variables are defined per container, not per project.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Okay, I guess I don't mind, maybe someone else has a preference.


Database specific values (will use SQLite if not set):

* `POSTGRES_DATABASE` - The database name for the synapse postgres database. [default: `matrix`]
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If so, the default also seems to be "synapse" too.

* `POSTGRES_HOST` - The host of the postgres database if you wish to use postgresql instead of sqlite3. [default: `db` which is useful when using a container on the same docker network in a compose file where the postgres service is called `db`]
* `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: `matrix`]
206 changes: 206 additions & 0 deletions contrib/docker/conf/homeserver.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,206 @@
# 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]
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd leave out the webclient. It's deprecated.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed.

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]
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See above.

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" }}"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

IMO synapse would be a better fit, for user and database.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed.

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 ##

{% if SYNAPSE_RECAPTCHA_PUBLIC_KEY %}
recaptcha_public_key: "{{ SYNAPSE_RECAPTCHA_PUBLIC_KEY }}"
recaptcha_private_key: "{{ SYNAPSE_RECAPTCHA_PRIVATE_KEY }}"
enable_registration_captcha: True
recaptcha_siteverify_api: "https://www.google.com/recaptcha/api/siteverify"
{% else %}
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"
{% endif %}

## Turn ##

{% if SYNAPSE_TURN_URIS %}
turn_uris:
{% for uri in SYNAPSE_TURN_URIS.split(',') %} - {{ uri }}
{% endfor %}
turn_shared_secret: "{{ SYNAPSE_TURN_SECRET }}"
turn_user_lifetime: "1h"
turn_allow_guests: True
{% else %}
turn_uris: []
turn_shared_secret: "YOUR_SHARED_SECRET"
turn_user_lifetime: "1h"
turn_allow_guests: True
{% endif %}

## 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
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why is this hardcoded when there is an env var for this?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My mistake, will fix.


## 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 <[email protected]>"
# 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
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would be nice to have some way to add appservices somehow (maybe in a future version of the Dockerfile).

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Definitely agree, I was thinking maybe have all yaml files in a folder in /data be included as appservices.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just added this in the latest commit.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Wouldn't it make a lot more sense to let the regular generate command take care of this? Having a complete config file here feels like duplicating what the generate command does. Adding the used environment variables as either command line flags to the generate command or having the generate command read the env vars itself would make this a lot more portable.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I want the image to have two different modes of operation: either generating and customizing a config file, or using the dnyamically generated one. I agree that the dynamically generated one could be populated using the generate command instead of Jinja inside the start script.

I'd say this is room for later improvement, as I'm not experimented enough to play with Synapse core code yet :)

36 changes: 36 additions & 0 deletions contrib/docker/conf/log.config
Original file line number Diff line number Diff line change
@@ -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]
Loading