1 Commits

7 changed files with 4 additions and 260 deletions

View File

@ -9,9 +9,6 @@ available.
## Roles ## Roles
- [`mastodon`](roles/mastodon/README.md): deployment using a container based
setup, able to use webfinger delegation.
## License ## License
[CNPLv7+](LICENSE.md): Cooperative Nonviolent Public License [CNPLv7+](LICENSE.md): Cooperative Nonviolent Public License

View File

@ -1,65 +0,0 @@
# `finallycoffee.fediverse.mastodon` ansible role
## Overview
This role aims to automate as much as possible with running a docker container
based mastodon setup. It provides you with the streaming container, sidekiq and
web (api) as well an nginx routing the application traffic.
You need to provide a postgresql database, the redis server, optionally an
elasticsearch instance and the mail server. Roles providing components are linked,
if applicable.
### Usage
The minimum configuration could be as follows:
```yaml
mastodon_domain: finally.coffee
# Optional, if you want to host your frontend + api somewhere else
mastodon_web_domain: frontend.some.website
# you need to provide and manage the following secrets
mastodon_secret_key: very_long_secret
mastodon_otp_secret: also_very_long_secret
mastodon_vapid_public_key: check_mastodon_docs_for_this
mastodon_vapid_private_key: see_above
```
#### Database
The database configuration is as follows:
```yaml
mastodon_database_host: postgres.local
mastodon_database_port: 5432 #optional, defaults to this
mastodon_database_user: mastodont
mastodon_database_pass: hopefully_secure
mastodon_database_name: mastodon
```
For seeding the database during initial deployment, you need to set
`mastodon_seed_database: true` exactly once (when it succeeds).
### Redis
As of writing this, it seems that atleast one component of mastodon can't
deal with a password for redis, leading to the need to run redis without
authentification for all components:
```yaml
mastodon_redis_url: unix:///var/run/redis/mastodon.sock
```
#### Mail
The mail server for verifications and notifications can be configured as followed:
```yaml
mastodon_mail_server: mail.example.org
mastodon_mail_user: mailuser@mydomain.org
mastodon_mail_password: very_secure_password_for_mailing_account
```
For further Configuration, see [`defaults/main.yml`](defaults/main.yml) to
override further keys for configuration

View File

@ -3,7 +3,6 @@
mastodon_user: mastodon mastodon_user: mastodon
mastodon_base_path: /opt/mastodon mastodon_base_path: /opt/mastodon
mastodon_domain: ~ mastodon_domain: ~
mastodon_web_domain: ~
mastodon_version: 3.5.1 mastodon_version: 3.5.1
mastodon_git_upstream_url: "https://github.com/mastodon/mastodon.git" mastodon_git_upstream_url: "https://github.com/mastodon/mastodon.git"
@ -11,14 +10,6 @@ mastodon_data_path: "{{ mastodon_base_path }}/data"
mastodon_repo_path: "{{ mastodon_base_path }}/src" mastodon_repo_path: "{{ mastodon_base_path }}/src"
mastodon_config_path: "{{ mastodon_base_path }}/config" mastodon_config_path: "{{ mastodon_base_path }}/config"
mastodon_config_env_file: "{{ mastodon_config_path }}/env.production" mastodon_config_env_file: "{{ mastodon_config_path }}/env.production"
mastodon_nginx_config_path: "{{ mastodon_base_path }}/nginx-config"
mastodon_nginx_config_file: "{{ mastodon_nginx_config_path }}/nginx.conf"
mastodon_nginx_cache_path: "{{ mastodon_base_path }}/nginx-cache"
mastodon_container_bind_ip: "127.0.0.1"
mastodon_streaming_backend: "{{ mastodon_container_bind_ip }}:4000"
mastodon_api_backend: "{{ mastodon_container_bind_ip }}:3000"
mastodon_backend: "{{ mastodon_container_bind_ip }}:5000"
mastodon_container_name: mastodon mastodon_container_name: mastodon
mastodon_container_name_sidekiq: "{{ mastodon_container_name }}_sidekiq" mastodon_container_name_sidekiq: "{{ mastodon_container_name }}_sidekiq"
@ -41,33 +32,17 @@ mastodon_container_volumes_sidekiq: >-
{{ mastodon_container_base_volumes_sidekiq + mastodon_container_extra_volumes_sidekiq }} {{ mastodon_container_base_volumes_sidekiq + mastodon_container_extra_volumes_sidekiq }}
mastodon_container_base_volumes: mastodon_container_base_volumes:
- "{{ mastodon_repo_path }}/public:/mastodon/public:z" - "{{ mastodon_repo_path }}/public/system:/mastodon/public/system:z"
mastodon_container_extra_volumes: [] mastodon_container_extra_volumes: []
mastodon_container_volumes: >- mastodon_container_volumes: >-
{{ mastodon_container_base_volumes + mastodon_container_extra_volumes }} {{ mastodon_container_base_volumes + mastodon_container_extra_volumes }}
mastodon_container_ports_streaming: mastodon_container_ports_streaming:
- "{{ mastodon_streaming_backend }}:4000" - "127.0.0.1:4000:4000"
mastodon_container_ports: mastodon_container_ports:
- "{{ mastodon_api_backend }}:3000" - "127.0.0.1:3000:3000"
mastodon_container_restart_policy: unless-stopped mastodon_container_restart_policy: unless-stopped
mastodon_nginx_version: 1.21.6
mastodon_nginx_server_name: "{{ mastodon_domain }}"
mastodon_container_nginx_name: "{{ mastodon_container_name }}_nginx"
mastodon_container_nginx_image_name: docker.io/library/nginx
mastodon_container_nginx_image_tag: ~
mastodon_container_nginx_image_flavour: alpine
mastodon_container_nginx_image: >-2
{{ mastodon_container_nginx_image_name }}:{{ mastodon_container_nginx_image_tag
| default(mastodon_nginx_version + ('-' + mastodon_container_nginx_image_flavour if mastodon_container_nginx_image_flavour else ''), True) }}
mastodon_container_nginx_working_directory: "/var/www/mastodon"
mastodon_container_nginx_cache_directory: "/var/cache/nginx"
mastodon_container_volumes_nginx:
- "{{ mastodon_nginx_config_file }}:/etc/nginx/conf.d/default.conf:ro"
- "{{ mastodon_repo_path }}/public:{{ mastodon_container_nginx_working_directory }}:ro"
- "{{ mastodon_nginx_cache_path }}:{{ mastodon_container_nginx_cache_directory }}:z"
mastodon_container_network_name: mastodon mastodon_container_network_name: mastodon
mastodon_secret_key: ~ mastodon_secret_key: ~
@ -77,7 +52,6 @@ mastodon_vapid_private_key: ~
mastodon_redis_host: ~ mastodon_redis_host: ~
mastodon_redis_port: ~ mastodon_redis_port: ~
mastodon_redis_url: ~
mastodon_redis_password: ~ mastodon_redis_password: ~
mastodon_redis_db_index: ~ mastodon_redis_db_index: ~

View File

@ -24,10 +24,3 @@
state: started state: started
restart: true restart: true
listen: restart-mastodon listen: restart-mastodon
- name: Restart mastodon nginx
docker_container:
name: "{{ mastodon_container_nginx_name }}"
state: started
restart: true
listen: restart-mastodon-nginx

View File

@ -21,8 +21,6 @@
- path: "{{ mastodon_data_path }}" - path: "{{ mastodon_data_path }}"
- path: "{{ mastodon_repo_path }}" - path: "{{ mastodon_repo_path }}"
mode: '0700' mode: '0700'
- path: "{{ mastodon_nginx_config_path }}"
- path: "{{ mastodon_nginx_cache_path }}"
loop_control: { label: "{{ item.path }}" } loop_control: { label: "{{ item.path }}" }
- name: Ensure environment file is templated - name: Ensure environment file is templated
@ -34,15 +32,6 @@
mode: "0640" mode: "0640"
notify: restart-mastodon notify: restart-mastodon
- name: Ensure reverse proxy configuration is templated
template:
src: nginx.conf.j2
dest: "{{ mastodon_nginx_config_file }}"
owner: "{{ mastodon_user_info.uid | default(mastodon_user) }}"
group: "{{ mastodon_user_info.group | default(mastodon_user) }}"
mode: "0640"
notify: restart-mastodon-nginx
- name: Ensure mastodon git repository is present and up-to-date - name: Ensure mastodon git repository is present and up-to-date
git: git:
repo: "{{ mastodon_git_upstream_url }}" repo: "{{ mastodon_git_upstream_url }}"
@ -54,14 +43,6 @@
track_submodules: yes track_submodules: yes
register: git_repo_info register: git_repo_info
- name: Ensure mastodon git repository and children belong to {{ mastodon_user }}
file:
path: "{{ mastodon_repo_path }}"
state: directory
recurse: yes
owner: "{{ mastodon_user }}"
group: "{{ mastodon_user }}"
- name: Ensure docker network for backend communication is created - name: Ensure docker network for backend communication is created
docker_network: docker_network:
name: "{{ mastodon_container_network_name }}" name: "{{ mastodon_container_network_name }}"
@ -80,17 +61,6 @@
GID: "{{ mastodon_user_info.group }}" GID: "{{ mastodon_user_info.group }}"
when: git_repo_info.before != git_repo_info.after when: git_repo_info.before != git_repo_info.after
- name: Ensure nginx reverse proxy image is present
docker_image:
name: "{{ mastodon_container_nginx_image }}"
state: present
source: pull
force_source: "{{ mastodon_container_nginx_image_tag|default(false, true) | bool }}"
register: masto_nginx_pull
until: masto_nginx_pull is succeeded
retries: 5
delay: 3
- name: Ensure database is seeded - name: Ensure database is seeded
docker_container: docker_container:
name: "{{ mastodon_container_name }}_setup_db" name: "{{ mastodon_container_name }}_setup_db"
@ -103,7 +73,6 @@
interactive: yes interactive: yes
detach: no detach: no
cleanup: yes cleanup: yes
when: mastodon_seed_database|default(false, true)
- name: Ensure mastodon sidekiq container '{{ mastodon_container_name_sidekiq }}' is running - name: Ensure mastodon sidekiq container '{{ mastodon_container_name_sidekiq }}' is running
docker_container: docker_container:
@ -148,29 +117,9 @@
command: "bash -c \"rm -f /mastodon/tmp/pids/server.pid; bundle exec rails s -p 3000\"" command: "bash -c \"rm -f /mastodon/tmp/pids/server.pid; bundle exec rails s -p 3000\""
restart_policy: "{{ mastodon_container_restart_policy }}" restart_policy: "{{ mastodon_container_restart_policy }}"
ports: "{{ mastodon_container_ports }}" ports: "{{ mastodon_container_ports }}"
user: "{{ mastodon_user }}"
healthcheck: healthcheck:
test: ["CMD-SHELL", "wget -q --spider --proxy=off localhost:3000/health || exit 1"] test: ["CMD-SHELL", "wget -q --spider --proxy=off localhost:3000/health || exit 1"]
interval: 5s interval: 5s
retries: 3 retries: 3
start_period: 0s start_period: 0s
timeout: 5s timeout: 5s
- name: Ensure mastodon-nginx container '{{ mastodon_container_nginx_name }}' is running
docker_container:
name: "{{ mastodon_container_nginx_name }}"
image: "{{ mastodon_container_nginx_image }}"
network_mode: host
volumes: "{{ mastodon_container_volumes_nginx }}"
restart_policy: "{{ mastodon_container_restart_policy }}"
- name: Ensure assets are precompiled
docker_container:
name: "{{ mastodon_container_name }}"
env_file: "{{ mastodon_config_env_file }}"
command: "bash -c \"bundle exec rails assets:precompile\""
user: "{{ mastodon_user }}"
tty: yes
interactive: yes
detach: no
when: git_repo_info.before != git_repo_info.after

View File

@ -15,26 +15,16 @@
# This identifies your server and cannot be changed safely later # This identifies your server and cannot be changed safely later
# ---------- # ----------
LOCAL_DOMAIN={{ mastodon_domain }} LOCAL_DOMAIN={{ mastodon_domain }}
{% if mastodon_web_domain|default(false, true) %}
WEB_DOMAIN={{ mastodon_web_domain }}
{% endif %}
# Redis # Redis
# ----- # -----
{% if mastodon_redis_host|default(false, true) %}
REDIS_HOST={{ mastodon_redis_host }} REDIS_HOST={{ mastodon_redis_host }}
{% endif %}
{% if mastodon_redis_port|default(false, true) %}
REDIS_PORT={{ mastodon_redis_port }} REDIS_PORT={{ mastodon_redis_port }}
{% endif %}
{% if mastodon_redis_url %}
REDIS_URL={{ mastodon_redis_url }}
{% endif %}
{% if mastodon_redis_password %} {% if mastodon_redis_password %}
REDIS_PASSWORD={{ mastodon_redis_password }} REDIS_PASSWORD={{ mastodon_redis_password }}
{% endif %} {% endif %}
{% if mastodon_redis_db_index %} {% if mastodon_redis_db_index %}
REDIS_DB_INDEX={{ mastodon_redis_db_index }} REDIS_PASSWORD={{ mastodon_redis_db_index }}
{% endif %} {% endif %}
# PostgreSQL # PostgreSQL

View File

@ -1,94 +0,0 @@
map $http_upgrade $connection_upgrade {
default upgrade;
'' close;
}
upstream backend {
server {{ mastodon_api_backend }} fail_timeout=0;
}
upstream streaming {
server {{ mastodon_streaming_backend }} fail_timeout=0;
}
proxy_cache_path {{ mastodon_container_nginx_cache_directory }} levels=1:2 keys_zone=CACHE:10m inactive=7d max_size=2g;
server {
listen {{ mastodon_backend }};
server_name {{ mastodon_nginx_server_name }};
keepalive_timeout 70;
sendfile on;
client_max_body_size 200m;
root {{ mastodon_container_nginx_working_directory }};
gzip on;
gzip_disable "msie6";
gzip_vary on;
gzip_proxied any;
gzip_comp_level 6;
gzip_buffers 16 8k;
gzip_http_version 1.1;
gzip_types text/plain text/css application/json application/javascript text/xml application/xml application/xml+rss text/javascript image/svg+xml image/x-icon;
location / {
try_files $uri @proxy;
}
location ~ ^/(emoji|packs|system/accounts/avatars|system/media_attachments/files) {
add_header Cache-Control "public, max-age=31536000, immutable";
add_header Strict-Transport-Security "max-age=31536000" always;
try_files $uri @proxy;
}
location /sw.js {
add_header Cache-Control "public, max-age=0";
add_header Strict-Transport-Security "max-age=31536000" always;
try_files $uri @proxy;
}
location @proxy {
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header Proxy "";
proxy_pass_header Server;
proxy_pass http://backend;
proxy_buffering on;
proxy_redirect off;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
proxy_cache CACHE;
proxy_cache_valid 200 7d;
proxy_cache_valid 410 24h;
proxy_cache_use_stale error timeout updating http_500 http_502 http_503 http_504;
add_header X-Cached $upstream_cache_status;
add_header Strict-Transport-Security "max-age=31536000" always;
tcp_nodelay on;
}
location /api/v1/streaming {
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header Proxy "";
proxy_pass http://streaming;
proxy_buffering off;
proxy_redirect off;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
tcp_nodelay on;
}
error_page 500 501 502 503 504 /500.html;
}