Login Logout

Howto Mastodon

Mastodon est un réseau social libre et décentralisé, en alternative à Twitter.

Installation

Nous installons la version 1.6.1 sous Debian 8 (Jessie).

Mastodon s’appuie sur Ruby, NodeJS, Yarn, Nginx, Redis et PostgreSQL.

On peut installer les dépendances pour Mastodon :

# apt install nodejs yarn imagemagick ffmpeg libpq-dev libxml2-dev libxslt1-dev file git curl \
g++ libprotobuf-dev protobuf-compiler pkg-config build-essential libreadline-dev libicu-dev libidn11-dev

Note : Vous devez avoir les backports jessie-backports pour installer ffmpeg.

Compte UNIX

Créer un compte UNIX mastodon :

# adduser --disabled-login --gecos 'Mastodon App' mastodon

Note : Assurez-vous d’avoir DIR_MODE=0750 dans /etc/adduser.conf pour créer le home en 750.

Ruby

Mastodon nécessite une version très récente de Ruby (2.4.1), on le met en place via rbenv :

# sudo -iu mastodon
$ git clone https://github.com/rbenv/rbenv.git ~/.rbenv
$ cd ~/.rbenv && src/configure && make -C src
$ echo 'export PATH="$HOME/.rbenv/bin:$PATH"' >> ~/.bash_profile
$ echo 'eval "$(rbenv init -)"' >> ~/.bash_profile
$ echo 'export RAILS_ENV="production"' >> ~/.bash_profile
$ source ~/.bash_profile
$ git clone https://github.com/rbenv/ruby-build.git ~/.rbenv/plugins/ruby-build
$ cd
$ TMPDIR=~/tmp MAKE_OPTS=-j$(nproc) rbenv install 2.4.1

Note : On met la variable d’environnement RAILS_ENV dans notre profile bash pour éviter de l’indiquer à chaque commande Ruby/Rails.

NodeJS et Yarn

Mastodon nécessite une version très récentes de NodeJS et Yarn :

# echo "deb http://deb.nodesource.com/node_6.x jessie main" > /etc/apt/sources.list.d/nodesource.list
# wget https://deb.nodesource.com/gpgkey/nodesource.gpg.key -O -|apt-key add -

# echo "deb http://dl.yarnpkg.com/debian/ stable main" > /etc/apt/sources.list.d/yarn.list
# wget https://dl.yarnpkg.com/debian/pubkey.gpg -O - | apt-key add -

# apt update
# apt install nodejs yarn

PostgreSQL

Mastodon utilise PostgreSQL. On utilise donc la version 9.4 de Debian Jessie :

# apt install postgresql postgresql-client libpq-dev postgresql-contrib

Création de l’utilisateur PostgreSQL :

# sudo -u postgres createuser mastodon -d -P -R

Note : On donne les droits CREATEDB car Mastodon doit faire un DROP DATABASE puis CREATE DATABASE lors de l’installation…

Note : Pensez à conserver le mot de passe pour le mettre par la suite (ou pas si utilisation de l’authentification via ident).

Redis

Installation classique :

# apt install redis-server

Mastodon

On clone le repository et installe avec bundle et yarn :

# sudo -iu mastodon
$ git clone https://github.com/tootsuite/mastodon.git
$ cd mastodon
$ git checkout v1.6.1
$ gem install bundler
$ bundle install --deployment --without development test
$ yarn install --pure-lockfile
$ cp .env.production.sample .env.production
$ bundle exec rake secret
$ bundle exec rake mastodon:webpush:generate_vapid_key >> .env.production

Attention, si vous avez un /home en noexec, il faudra le passer en exec pour les processus Ruby et NPM. Au risque d’obtenir ce genre d’erreurs :

npm[2990]: Error: Compilation of µWebSockets has failed and there is no pre-compiled binary available for your system. Please install a > supported C++11 compiler and reinstall the module 'uws'.
Failed at step EXEC spawning /home/mastodon/.rbenv/shims/bundle: Permission denied

On édite le fichier fichier .env.production à notre convenance, voici un exemple :

REDIS_HOST=127.0.0.1
REDIS_PORT=6379
DB_HOST=127.0.0.1
DB_USER=mastodon
DB_NAME=mastodon_production
DB_PASS=PASSWORD
DB_PORT=5432

LOCAL_DOMAIN=mastodon.example.com
LOCAL_HTTPS=true

PAPERCLIP_SECRET=PASSWORD
SECRET_KEY_BASE=PASSWORD
OTP_SECRET=PASSWORD

EMAIL_DOMAIN_WHITELIST=example.com

DEFAULT_LOCALE=fr

SMTP_SERVER=127.0.0.1
SMTP_PORT=25
SMTP_LOGIN=
SMTP_PASSWORD=
SMTP_FROM_ADDRESS=mastodon@mastodon.example.com
#SMTP_DOMAIN= # defaults to LOCAL_DOMAIN
#SMTP_DELIVERY_METHOD=smtp # delivery method can also be sendmail
SMTP_AUTH_METHOD=none
SMTP_OPENSSL_VERIFY_MODE=none

Initialisation de la base de données :

$ bundle exec rails db:setup

Compilation des assets :

$ bundle exec rails assets:precompile
$ chmod -R u=rwX,g=rwX,o=rX /home/mastodon/mastodon/public

Unités systemd

Unités systemd à mettre dans /etc/systemd/system

mastodon-web.service

[Unit]
Description=mastodon-web
After=network.target

[Service]
Type=simple
User=mastodon
WorkingDirectory=/home/mastodon/mastodon
Environment="RAILS_ENV=production"
Environment="PORT=3000"
ExecStart=/home/mastodon/.rbenv/shims/bundle exec puma -C config/puma.rb
TimeoutSec=15
Restart=always

[Install]
WantedBy=multi-user.target

mastodon-sidekiq.service

[Unit]
Description=mastodon-sidekiq
After=network.target

[Service]
Type=simple
User=mastodon
WorkingDirectory=/home/mastodon/mastodon
Environment="RAILS_ENV=production"
Environment="DB_POOL=5"
ExecStart=/home/mastodon/.rbenv/shims/bundle exec sidekiq -c 5 -q default -q mailers -q pull -q push
TimeoutSec=15
Restart=always

[Install]
WantedBy=multi-user.target

mastodon-streaming.service

[Unit]
Description=mastodon-streaming
After=network.target

[Service]
Type=simple
User=mastodon
WorkingDirectory=/home/mastodon/mastodon
Environment="NODE_ENV=production"
Environment="PORT=4000"
ExecStart=/usr/bin/npm run start
TimeoutSec=15
Restart=always

[Install]
WantedBy=multi-user.target

On active et on démarre les unités :

# systemctl enable mastodon-{web,sidekiq,streaming}
# systemctl start mastodon-{web,sidekiq,streaming}

Crontab

RAILS_ENV=production
@daily cd /home/mastodon/mastodon && /home/mastodon/.rbenv/shims/bundle exec rake mastodon:daily > /dev/null

Nginx

On utilise Nginx :

# apt install nginx-full

Exemple de vhost :

map $http_upgrade $connection_upgrade {
  default upgrade;
  ''      close;
}

server {
  listen 80;
  listen [::]:80;
  server_name example.com;
  # Useful for Let's Encrypt
  location /.well-known/acme-challenge/ { allow all; }
  location / { return 301 https://$host$request_uri; }
}

server {
  listen 443 ssl http2;
  listen [::]:443 ssl http2;
  server_name example.com;

  ssl_protocols TLSv1.2;
  ssl_ciphers HIGH:!MEDIUM:!LOW:!aNULL:!NULL:!SHA;
  ssl_prefer_server_ciphers on;
  ssl_session_cache shared:SSL:10m;

  ssl_certificate     /etc/letsencrypt/live/example.com/fullchain.pem;
  ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem;

  keepalive_timeout    70;
  sendfile             on;
  client_max_body_size 0;

  root /home/mastodon/mastodon/public;

  gzip on;
  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;

  add_header Strict-Transport-Security "max-age=31536000";

  location / {
    try_files $uri @proxy;
  }

  location ~ ^/(packs|system/media_attachments/files|system/accounts/avatars) {
    add_header Cache-Control "public, max-age=31536000, immutable";
    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 https;
    proxy_set_header Proxy "";
    proxy_pass_header Server;

    proxy_pass http://127.0.0.1:3000;
    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;
  }

  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 https;
    proxy_set_header Proxy "";

    proxy_pass http://127.0.0.1:4000;
    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;
}

Note : La partie SSL/TLS n’est pas évoquée. À vous de faire le nécessaire avec un certificat Let’s Encrypt par exemple. N’oubliez donc pas de modifier les directives ssl_ dans le vhost.

Mises à jour

Le principe des mises à jour est basé sur un git pull et un git checkout.

# sudo -iu mastodon
$ cd mastodon
$ git fetch
$ git checkout <VERSION>
$ bundle install --deployment --without development test
$ bundle exec rails db:migrate
$ yarn install --pure-lockfile
$ bundle exec rails assets:precompile
$ chmod -R u=rwX,g=rwX,o=rX /home/mastodon/mastodon/public
$ exit
# systemctl restart mastodon-*.service

Note : Ces commandes génériques ne sont parfois pas suffisantes. Pensez à lire les notes de versions.

Configuration

Pour restreindre l’inscription à certains domaines de messagerie :

EMAIL_DOMAIN_WHITELIST=example.com|example.org

Utilisation

On peut utiliser différents clients :

  • L’interface web via un navigateur
  • Twidere sous Android ou iOS
  • Amaroq sous iOS

FAQ

À propos des logs

Mastodon n’a aucun fichier de logs. Les logs sont gérés via la sortie standard et vont donc dans journald. On consultera les logs avec journalctl -u mastodon-SERVICE.