]> git.immae.eu Git - perso/Immae/Config/Nix.git/blame - nixops/modules/websites/tools/mastodon.nix
Move secrets module outside of nixops
[perso/Immae/Config/Nix.git] / nixops / modules / websites / tools / mastodon.nix
CommitLineData
a4993193 1{ lib, pkgs, config, myconfig, mylibs, ... }:
35a397cd 2let
eb14b976
IB
3 varDir = "/var/lib/mastodon_immae";
4 socketsDir = "/run/mastodon";
5 nodeSocket = "${socketsDir}/live_immae_node.sock";
6 railsSocket = "${socketsDir}/live_immae_puma.sock";
7
8 mastodon = pkgs.webapps.mastodon.override { inherit varDir; };
35a397cd 9
eb14b976 10 env = myconfig.env.tools.mastodon;
a95ab089 11 root = "/run/current-system/webapps/tools_mastodon";
35a397cd
IB
12 cfg = config.services.myWebsites.tools.mastodon;
13in {
14 options.services.myWebsites.tools.mastodon = {
15 enable = lib.mkEnableOption "enable mastodon's website";
16 };
17
18 config = lib.mkIf cfg.enable {
1a718805 19 secrets.keys = [{
eb14b976
IB
20 dest = "webapps/tools-mastodon";
21 user = "mastodon";
22 group = "mastodon";
23 permissions = "0400";
24 text = ''
25 REDIS_HOST=${env.redis.host}
26 REDIS_PORT=${env.redis.port}
27 REDIS_DB=${env.redis.db}
28 DB_HOST=${env.postgresql.socket}
29 DB_USER=${env.postgresql.user}
30 DB_NAME=${env.postgresql.database}
31 DB_PASS=${env.postgresql.password}
32 DB_PORT=${env.postgresql.port}
33
34 LOCAL_DOMAIN=mastodon.immae.eu
35 LOCAL_HTTPS=true
36 ALTERNATE_DOMAINS=immae.eu
37
38 PAPERCLIP_SECRET=${env.paperclip_secret}
39 SECRET_KEY_BASE=${env.secret_key_base}
40 OTP_SECRET=${env.otp_secret}
41
42 VAPID_PRIVATE_KEY=${env.vapid.private}
43 VAPID_PUBLIC_KEY=${env.vapid.public}
44
45 SMTP_DELIVERY_METHOD=sendmail
46 SMTP_FROM_ADDRESS=mastodon@tools.immae.eu
47 SENDMAIL_LOCATION="/run/wrappers/bin/sendmail"
48 PAPERCLIP_ROOT_PATH=${varDir}
49
50 STREAMING_CLUSTER_NUM=1
51
52 RAILS_LOG_LEVEL=warn
53
54 # LDAP authentication (optional)
55 LDAP_ENABLED=true
56 LDAP_HOST=ldap.immae.eu
57 LDAP_PORT=636
58 LDAP_METHOD=simple_tls
59 LDAP_BASE="dc=immae,dc=eu"
60 LDAP_BIND_DN="cn=mastodon,ou=services,dc=immae,dc=eu"
61 LDAP_PASSWORD="${env.ldap.password}"
62 LDAP_UID="uid"
63 LDAP_SEARCH_FILTER="(&(%{uid}=%{email})(memberOf=cn=users,cn=mastodon,ou=services,dc=immae,dc=eu))"
64 '';
65 }];
66 ids.uids.mastodon = env.user.uid;
67 ids.gids.mastodon = env.user.gid;
35a397cd
IB
68
69 users.users.mastodon = {
70 name = "mastodon";
71 uid = config.ids.uids.mastodon;
72 group = "mastodon";
73 description = "Mastodon user";
eb14b976 74 home = varDir;
35a397cd
IB
75 useDefaultShell = true;
76 };
77
78 users.groups.mastodon.gid = config.ids.gids.mastodon;
79
80 systemd.services.mastodon-streaming = {
81 description = "Mastodon Streaming";
82 wantedBy = [ "multi-user.target" ];
83 after = [ "network.target" "mastodon-web.service" ];
84
85 environment.NODE_ENV = "production";
eb14b976 86 environment.SOCKET = nodeSocket;
35a397cd
IB
87
88 path = [ pkgs.nodejs pkgs.bashInteractive ];
89
90 script = ''
91 exec npm run start
92 '';
93
94 postStart = ''
95 while [ ! -S $SOCKET ]; do
96 sleep 0.5
97 done
98 chmod a+w $SOCKET
99 '';
100
101 postStop = ''
102 rm $SOCKET
103 '';
104
105 serviceConfig = {
106 User = "mastodon";
32c84ff8 107 EnvironmentFile = "/var/secrets/webapps/tools-mastodon";
35a397cd
IB
108 PrivateTmp = true;
109 Restart = "always";
110 TimeoutSec = 15;
111 Type = "simple";
eb14b976 112 WorkingDirectory = mastodon;
35a397cd
IB
113 };
114
eb14b976 115 unitConfig.RequiresMountsFor = varDir;
35a397cd
IB
116 };
117
118 systemd.services.mastodon-web = {
119 description = "Mastodon Web app";
120 wantedBy = [ "multi-user.target" ];
121 after = [ "network.target" ];
122
123 environment.RAILS_ENV = "production";
61199e93 124 environment.BUNDLE_PATH = "${mastodon.gems}/${mastodon.gems.ruby.gemPath}";
2ff7e086 125 environment.BUNDLE_GEMFILE = "${mastodon.gems.confFiles}/Gemfile";
eb14b976 126 environment.SOCKET = railsSocket;
35a397cd 127
2ff7e086 128 path = [ mastodon.gems mastodon.gems.ruby pkgs.file ];
35a397cd
IB
129
130 preStart = ''
2ff7e086 131 ./bin/bundle exec rails db:migrate
35a397cd
IB
132 '';
133
134 script = ''
2ff7e086 135 exec ./bin/bundle exec puma -C config/puma.rb
35a397cd
IB
136 '';
137
138 serviceConfig = {
139 User = "mastodon";
32c84ff8 140 EnvironmentFile = "/var/secrets/webapps/tools-mastodon";
35a397cd
IB
141 PrivateTmp = true;
142 Restart = "always";
d65bf723 143 TimeoutSec = 60;
35a397cd 144 Type = "simple";
eb14b976 145 WorkingDirectory = mastodon;
35a397cd
IB
146 };
147
eb14b976 148 unitConfig.RequiresMountsFor = varDir;
35a397cd
IB
149 };
150
151 systemd.services.mastodon-sidekiq = {
152 description = "Mastodon Sidekiq";
153 wantedBy = [ "multi-user.target" ];
154 after = [ "network.target" "mastodon-web.service" ];
155
156 environment.RAILS_ENV="production";
2ff7e086
IB
157 environment.BUNDLE_PATH = "${mastodon.gems}/${mastodon.gems.ruby.gemPath}";
158 environment.BUNDLE_GEMFILE = "${mastodon.gems.confFiles}/Gemfile";
35a397cd
IB
159 environment.DB_POOL="5";
160
2ff7e086 161 path = [ mastodon.gems mastodon.gems.ruby pkgs.imagemagick pkgs.ffmpeg pkgs.file ];
35a397cd
IB
162
163 script = ''
2ff7e086 164 exec ./bin/bundle exec sidekiq -c 5 -q default -q mailers -q pull -q push
35a397cd
IB
165 '';
166
167 serviceConfig = {
168 User = "mastodon";
32c84ff8 169 EnvironmentFile = "/var/secrets/webapps/tools-mastodon";
35a397cd
IB
170 PrivateTmp = true;
171 Restart = "always";
172 TimeoutSec = 15;
173 Type = "simple";
eb14b976 174 WorkingDirectory = mastodon;
35a397cd
IB
175 };
176
eb14b976 177 unitConfig.RequiresMountsFor = varDir;
35a397cd
IB
178 };
179
35a397cd
IB
180 system.activationScripts.mastodon = {
181 deps = [ "users" ];
182 text = ''
eb14b976
IB
183 install -m 0755 -o mastodon -g mastodon -d ${socketsDir}
184 install -m 0755 -o mastodon -g mastodon -d ${varDir} ${varDir}/tmp/cache
35a397cd
IB
185 '';
186 };
187
188 services.myWebsites.tools.modules = [
a952acc4 189 "headers" "proxy" "proxy_wstunnel" "proxy_http"
35a397cd
IB
190 ];
191 security.acme.certs."eldiron".extraDomains."mastodon.immae.eu" = null;
a95ab089
IB
192 system.extraSystemBuilderCmds = ''
193 mkdir -p $out/webapps
eb14b976 194 ln -s ${mastodon}/public/ $out/webapps/tools_mastodon
a95ab089 195 '';
35a397cd
IB
196 services.myWebsites.tools.vhostConfs.mastodon = {
197 certName = "eldiron";
198 hosts = ["mastodon.immae.eu" ];
a95ab089 199 root = root;
35a397cd
IB
200 extraConfig = [ ''
201 Header always set Referrer-Policy "strict-origin-when-cross-origin"
202 Header always set Strict-Transport-Security "max-age=31536000"
203
204 <LocationMatch "^/(assets|avatars|emoji|headers|packs|sounds|system)>
205 Header always set Cache-Control "public, max-age=31536000, immutable"
206 Require all granted
207 </LocationMatch>
208
209 ProxyPreserveHost On
210 RequestHeader set X-Forwarded-Proto "https"
211
212 RewriteEngine On
213
214 ProxyPass /500.html !
215 ProxyPass /sw.js !
216 ProxyPass /embed.js !
217 ProxyPass /robots.txt !
218 ProxyPass /manifest.json !
219 ProxyPass /browserconfig.xml !
220 ProxyPass /mask-icon.svg !
221 ProxyPassMatch ^(/.*\.(png|ico|gif)$) !
222 ProxyPassMatch ^/(assets|avatars|emoji|headers|packs|sounds|system|.well-known/acme-challenge) !
223
eb14b976
IB
224 RewriteRule ^/api/v1/streaming/(.+)$ unix://${nodeSocket}|http://mastodon.immae.eu/api/v1/streaming/$1 [P,NE,QSA,L]
225 RewriteRule ^/api/v1/streaming/$ unix://${nodeSocket}|ws://mastodon.immae.eu/ [P,NE,QSA,L]
226 ProxyPass / unix://${railsSocket}|http://mastodon.immae.eu/
227 ProxyPassReverse / unix://${railsSocket}|http://mastodon.immae.eu/
35a397cd 228
eb14b976 229 Alias /system ${varDir}
35a397cd 230
eb14b976 231 <Directory ${varDir}>
35a397cd
IB
232 Require all granted
233 Options -MultiViews
234 </Directory>
235
a95ab089 236 <Directory ${root}>
35a397cd
IB
237 Require all granted
238 Options -MultiViews +FollowSymlinks
239 </Directory>
240
241 ErrorDocument 500 /500.html
242 ErrorDocument 501 /500.html
243 ErrorDocument 502 /500.html
244 ErrorDocument 503 /500.html
245 ErrorDocument 504 /500.html
246 '' ];
247 };
248 };
249}