]> git.immae.eu Git - perso/Immae/Config/Nix.git/blob - modules/private/websites/tools/cloud/farm.nix
Migrate php sessions to redis
[perso/Immae/Config/Nix.git] / modules / private / websites / tools / cloud / farm.nix
1 { lib, pkgs, config, ... }:
2 let
3 cfg = config.myServices.tools.cloud.farm;
4 apacheUser = config.services.httpd.Prod.user;
5 apacheGroup = config.services.httpd.Prod.group;
6 toVardir = name: "/var/lib/nextcloud_farm/${name}";
7 varDirs = lib.mapAttrsToList (name: v: toVardir name) cfg.instances;
8 toPhpBaseDir = name: builtins.concatStringsSep ":" ([ cfg.rootDirs."${name}" (toVardir name) ] ++ cfg.rootDirs."${name}".apps);
9 toVhost = name: ''
10 SetEnvIf Authorization "(.*)" HTTP_AUTHORIZATION=$1
11 SetEnv NEXTCLOUD_CONFIG_DIR "${toVardir name}"
12 <Directory ${cfg.rootDirs."${name}"}>
13 AcceptPathInfo On
14 DirectoryIndex index.php
15 Options FollowSymlinks
16 Require all granted
17 AllowOverride all
18
19 <IfModule mod_headers.c>
20 Header always set Strict-Transport-Security "max-age=15552000; includeSubDomains; preload"
21 </IfModule>
22 <FilesMatch "\.php$">
23 CGIPassAuth on
24 SetHandler "proxy:unix:${config.services.phpfpm.pools.${"nextcloud_farm_" + name}.socket}|fcgi://localhost"
25 </FilesMatch>
26
27 </Directory>
28 '';
29 phpPackage = (pkgs.php74.withExtensions({ enabled, all }: enabled ++ [ all.redis all.apcu all.opcache all.imagick ])).override { extraConfig = ''
30 apc.enable_cli = 1
31 '';
32 };
33 in
34 {
35 options.myServices.tools.cloud.farm = {
36 instances = lib.mkOption {
37 description = "Instances names for the nextcloud Farm";
38 default = {};
39 type = lib.types.attrsOf (lib.types.submodule {
40 options = {
41 nextcloud = lib.mkOption {
42 description = "Nextcloud version to use";
43 default = pkgs.webapps.nextcloud_20;
44 type = lib.types.package;
45 };
46 apps = lib.mkOption {
47 description = "Applications to use";
48 default = a: [];
49 #type = functionTo (listOf packages)
50 type = lib.types.unspecified;
51 };
52 };
53 });
54 };
55 rootDirs = lib.mkOption {
56 description = "Instance root dirs";
57 readOnly = true;
58 type = lib.types.attrsOf lib.types.package;
59 default = lib.mapAttrs (name: v: (v.nextcloud.override { varDir = null; }).withApps v.apps) cfg.instances;
60 };
61 vhosts = lib.mkOption {
62 description = "Instance vhosts configs";
63 readOnly = true;
64 type = lib.types.attrsOf lib.types.str;
65 default = lib.mapAttrs (name: v: toVhost name) cfg.instances;
66 };
67 };
68
69 config = lib.mkIf (builtins.length (builtins.attrNames cfg.instances) > 0) {
70 system.activationScripts.cloud_farm_vardirs = {
71 deps = [ "httpd" ];
72 text = ''
73 install -m 0755 -o ${apacheUser} -g ${apacheGroup} -d ${builtins.concatStringsSep " " varDirs}
74 '';
75 };
76 systemd.services = lib.mapAttrs' (k: v: lib.nameValuePair ("phpfpm-nextcloud_farm_" + k) {
77 after = lib.mkAfter [ "postgresql.service" ];
78 wants = [ "postgresql.service" ];
79 }) cfg.instances;
80 services.phpfpm.pools = lib.mapAttrs' (k: v: lib.nameValuePair ("nextcloud_farm_" + k) {
81 user = apacheUser;
82 group = apacheGroup;
83 settings = {
84 "listen.owner" = apacheUser;
85 "listen.group" = apacheGroup;
86 "pm" = "dynamic";
87 "pm.max_children" = "60";
88 "pm.start_servers" = "3";
89 "pm.min_spare_servers" = "3";
90 "pm.max_spare_servers" = "3";
91 "pm.process_idle_timeout" = "60";
92
93 "php_admin_value[output_buffering]" = "0";
94 "php_admin_value[max_execution_time]" = "1800";
95 "php_admin_value[zend_extension]" = "opcache";
96 "php_value[apcu.enable_cli]" = "1";
97 "php_value[apcu.enabled]" = "1";
98 #already enabled by default?
99 #"php_value[opcache.enable]" = "1";
100 "php_value[opcache.enable_cli]" = "1";
101 "php_value[opcache.interned_strings_buffer]" = "8";
102 "php_value[opcache.max_accelerated_files]" = "10000";
103 "php_value[opcache.memory_consumption]" = "128";
104 "php_value[opcache.save_comments]" = "1";
105 "php_value[opcache.revalidate_freq]" = "1";
106 "php_admin_value[memory_limit]" = "512M";
107
108 "php_admin_value[open_basedir]" = "/run/wrappers/bin/sendmail:${toPhpBaseDir k}:/proc/meminfo:/dev/urandom:/proc/self/fd:/tmp";
109 "php_admin_value[session.save_handler]" = "redis";
110 "php_admin_value[session.save_path]" = "'unix:///run/redis-php-sessions/redis.sock?persistent=1&prefix=Tools:NextcloudFarm:${k}:'";
111 };
112 inherit phpPackage;
113 }) cfg.instances;
114 users.users.root.packages = let
115 toOcc = name: pkgs.writeScriptBin "nextcloud-occ-${name}" ''
116 #! ${pkgs.stdenv.shell}
117 cd ${cfg.rootDirs."${name}"}
118 NEXTCLOUD_CONFIG_DIR="${toVardir name}" \
119 exec \
120 sudo -E -u wwwrun ${phpPackage}/bin/php \
121 -c ${phpPackage}/etc/php.ini \
122 occ $*
123 '';
124 in lib.mapAttrsToList (name: v: toOcc name) cfg.instances;
125 services.cron = {
126 enable = true;
127 systemCronJobs = let
128 toScript = name: pkgs.writeScriptBin "nextcloud-cron" ''
129 #! ${pkgs.stdenv.shell}
130 export LOCALE_ARCHIVE=/run/current-system/sw/lib/locale/locale-archive
131 export PATH=/run/wrappers/bin:$PATH
132 export NEXTCLOUD_CONFIG_DIR="${toVardir name}"
133 ${phpPackage}/bin/php -c ${phpPackage}/etc/php.ini -d memory_limit=512M -f ${cfg.rootDirs."${name}"}/cron.php
134 '';
135 toLine = name: ''
136 */15 * * * * wwwrun ${toScript name}/bin/nextcloud-cron
137 '';
138 in lib.mapAttrsToList (name: v: toLine name) cfg.instances;
139 };
140 };
141 }