grafana-alloy: don't build the frontend twice
[NixPkgs.git] / nixos / modules / services / network-filesystems / openafs / server.nix
blob8186277b4777523f573d777176ab1b55763b44ab
1 { config, lib, pkgs, ... }:
3 # openafsBin, openafsSrv, mkCellServDB
4 with import ./lib.nix { inherit config lib pkgs; };
6 let
7   inherit (lib) concatStringsSep literalExpression mkIf mkOption mkEnableOption
8   mkPackageOption optionalString types;
10   bosConfig = pkgs.writeText "BosConfig" (''
11     restrictmode 1
12     restarttime 16 0 0 0 0
13     checkbintime 3 0 5 0 0
14   '' + (optionalString cfg.roles.database.enable ''
15     bnode simple vlserver 1
16     parm ${openafsSrv}/libexec/openafs/vlserver ${optionalString cfg.dottedPrincipals "-allow-dotted-principals"} ${cfg.roles.database.vlserverArgs}
17     end
18     bnode simple ptserver 1
19     parm ${openafsSrv}/libexec/openafs/ptserver ${optionalString cfg.dottedPrincipals "-allow-dotted-principals"} ${cfg.roles.database.ptserverArgs}
20     end
21   '') + (optionalString cfg.roles.fileserver.enable ''
22     bnode dafs dafs 1
23     parm ${openafsSrv}/libexec/openafs/dafileserver ${optionalString cfg.dottedPrincipals "-allow-dotted-principals"} -udpsize ${udpSizeStr} ${cfg.roles.fileserver.fileserverArgs}
24     parm ${openafsSrv}/libexec/openafs/davolserver ${optionalString cfg.dottedPrincipals "-allow-dotted-principals"} -udpsize ${udpSizeStr} ${cfg.roles.fileserver.volserverArgs}
25     parm ${openafsSrv}/libexec/openafs/salvageserver ${cfg.roles.fileserver.salvageserverArgs}
26     parm ${openafsSrv}/libexec/openafs/dasalvager ${cfg.roles.fileserver.salvagerArgs}
27     end
28   '') + (optionalString (cfg.roles.database.enable && cfg.roles.backup.enable && (!cfg.roles.backup.enableFabs)) ''
29     bnode simple buserver 1
30     parm ${openafsSrv}/libexec/openafs/buserver ${cfg.roles.backup.buserverArgs} ${optionalString useBuCellServDB "-cellservdb /etc/openafs/backup/"}
31     end
32   '') + (optionalString (cfg.roles.database.enable &&
33                          cfg.roles.backup.enable &&
34                          cfg.roles.backup.enableFabs) ''
35     bnode simple buserver 1
36     parm ${lib.getBin pkgs.fabs}/bin/fabsys server --config ${fabsConfFile} ${cfg.roles.backup.fabsArgs}
37     end
38   ''));
40   netInfo = if (cfg.advertisedAddresses != []) then
41     pkgs.writeText "NetInfo" ((concatStringsSep "\nf " cfg.advertisedAddresses) + "\n")
42   else null;
44   buCellServDB = pkgs.writeText "backup-cellServDB-${cfg.cellName}"
45     (mkCellServDB cfg.cellName cfg.roles.backup.cellServDB);
47   useBuCellServDB = (cfg.roles.backup.cellServDB != []) && (!cfg.roles.backup.enableFabs);
49   cfg = config.services.openafsServer;
51   udpSizeStr = toString cfg.udpPacketSize;
53   fabsConfFile = pkgs.writeText "fabs.yaml" (builtins.toJSON ({
54     afs = {
55       aklog = cfg.package + "/bin/aklog";
56       cell = cfg.cellName;
57       dumpscan = cfg.package + "/bin/afsdump_scan";
58       fs = cfg.package + "/bin/fs";
59       pts = cfg.package + "/bin/pts";
60       vos = cfg.package + "/bin/vos";
61     };
62     k5start.command = (lib.getBin pkgs.kstart) + "/bin/k5start";
63   } // cfg.roles.backup.fabsExtraConfig));
65 in {
67   options = {
69     services.openafsServer = {
71       enable = mkOption {
72         default = false;
73         type = types.bool;
74         description = ''
75           Whether to enable the OpenAFS server. An OpenAFS server needs a
76           complex setup. So, be aware that enabling this service and setting
77           some options does not give you a turn-key-ready solution. You need
78           at least a running Kerberos 5 setup, as OpenAFS relies on it for
79           authentication. See the Guide "QuickStartUnix" coming with
80           `pkgs.openafs.doc` for complete setup
81           instructions.
82         '';
83       };
85       advertisedAddresses = mkOption {
86         type = types.listOf types.str;
87         default = [];
88         description = "List of IP addresses this server is advertised under. See NetInfo(5)";
89       };
91       cellName = mkOption {
92         default = "";
93         type = types.str;
94         description = "Cell name, this server will serve.";
95         example = "grand.central.org";
96       };
98       cellServDB = mkOption {
99         default = [];
100         type = with types; listOf (submodule [ { options = cellServDBConfig;} ]);
101         description = "Definition of all cell-local database server machines.";
102       };
104       package = mkPackageOption pkgs "openafs" { };
106       roles = {
107         fileserver = {
108           enable = mkOption {
109             default = true;
110             type = types.bool;
111             description = "Fileserver role, serves files and volumes from its local storage.";
112           };
114           fileserverArgs = mkOption {
115             default = "-vattachpar 128 -vhashsize 11 -L -rxpck 400 -cb 1000000";
116             type = types.str;
117             description = "Arguments to the dafileserver process. See its man page.";
118           };
120           volserverArgs = mkOption {
121             default = "";
122             type = types.str;
123             description = "Arguments to the davolserver process. See its man page.";
124             example = "-sync never";
125           };
127           salvageserverArgs = mkOption {
128             default = "";
129             type = types.str;
130             description = "Arguments to the salvageserver process. See its man page.";
131             example = "-showlog";
132           };
134           salvagerArgs = mkOption {
135             default = "";
136             type = types.str;
137             description = "Arguments to the dasalvager process. See its man page.";
138             example = "-showlog -showmounts";
139           };
140         };
142         database = {
143           enable = mkOption {
144             default = true;
145             type = types.bool;
146             description = ''
147               Database server role, maintains the Volume Location Database,
148               Protection Database (and Backup Database, see
149               `backup` role). There can be multiple
150               servers in the database role for replication, which then need
151               reliable network connection to each other.
153               Servers in this role appear in AFSDB DNS records or the
154               CellServDB.
155             '';
156           };
158           vlserverArgs = mkOption {
159             default = "";
160             type = types.str;
161             description = "Arguments to the vlserver process. See its man page.";
162             example = "-rxbind";
163           };
165           ptserverArgs = mkOption {
166             default = "";
167             type = types.str;
168             description = "Arguments to the ptserver process. See its man page.";
169             example = "-restricted -default_access S---- S-M---";
170           };
171         };
173         backup = {
174           enable = mkEnableOption ''
175             the backup server role. When using OpenAFS built-in buserver, use in conjunction with the
176             `database` role to maintain the Backup
177             Database. Normally only used in conjunction with tape storage
178             or IBM's Tivoli Storage Manager.
180             For a modern backup server, enable this role and see
181             {option}`enableFabs`
182           '';
184           enableFabs = mkEnableOption ''
185             FABS, the flexible AFS backup system. It stores volumes as dump files, relying on other
186             pre-existing backup solutions for handling them
187           '';
189           buserverArgs = mkOption {
190             default = "";
191             type = types.str;
192             description = "Arguments to the buserver process. See its man page.";
193             example = "-p 8";
194           };
196           cellServDB = mkOption {
197             default = [];
198             type = with types; listOf (submodule [ { options = cellServDBConfig;} ]);
199             description = ''
200               Definition of all cell-local backup database server machines.
201               Use this when your cell uses less backup database servers than
202               other database server machines.
203             '';
204           };
206           fabsArgs = mkOption {
207             default = "";
208             type = types.str;
209             description = ''
210               Arguments to the fabsys process. See
211               {manpage}`fabsys_server(1)` and
212               {manpage}`fabsys_config(1)`.
213             '';
214           };
216           fabsExtraConfig = mkOption {
217             default = {};
218             type = types.attrs;
219             description = ''
220               Additional configuration parameters for the FABS backup server.
221             '';
222             example = literalExpression ''
223             {
224               afs.localauth = true;
225               afs.keytab = config.sops.secrets.fabsKeytab.path;
226             }
227             '';
228           };
229         };
230       };
232       dottedPrincipals= mkOption {
233         default = false;
234         type = types.bool;
235         description = ''
236           If enabled, allow principal names containing (.) dots. Enabling
237           this has security implications!
238         '';
239       };
241       udpPacketSize = mkOption {
242         default = 1310720;
243         type = types.int;
244         description = ''
245           UDP packet size to use in Bytes. Higher values can speed up
246           communications. The default of 1 MB is a sufficient in most
247           cases. Make sure to increase the kernel's UDP buffer size
248           accordingly via `net.core(w|r|opt)mem_max`
249           sysctl.
250         '';
251       };
253     };
255   };
257   config = mkIf cfg.enable {
259     assertions = [
260       { assertion = cfg.cellServDB != [];
261         message = "You must specify all cell-local database servers in config.services.openafsServer.cellServDB.";
262       }
263       { assertion = cfg.cellName != "";
264         message = "You must specify the local cell name in config.services.openafsServer.cellName.";
265       }
266     ];
268     environment.systemPackages = [ openafsBin ];
270     environment.etc = {
271       bosConfig = {
272         source = bosConfig;
273         target = "openafs/BosConfig";
274         mode = "0644";
275       };
276       cellServDB = {
277         text = mkCellServDB cfg.cellName cfg.cellServDB;
278         target = "openafs/server/CellServDB";
279         mode = "0644";
280       };
281       thisCell = {
282         text = cfg.cellName;
283         target = "openafs/server/ThisCell";
284         mode = "0644";
285       };
286       buCellServDB = {
287         enable = useBuCellServDB;
288         text = mkCellServDB cfg.cellName cfg.roles.backup.cellServDB;
289         target = "openafs/backup/CellServDB";
290       };
291     };
293     systemd.services = {
294       openafs-server = {
295         description = "OpenAFS server";
296         after = [ "network.target" ];
297         wantedBy = [ "multi-user.target" ];
298         restartIfChanged = false;
299         unitConfig.ConditionPathExists = [
300           "|/etc/openafs/server/KeyFileExt"
301         ];
302         preStart = ''
303           mkdir -m 0755 -p /var/openafs
304           ${optionalString (netInfo != null) "cp ${netInfo} /var/openafs/netInfo"}
305           ${optionalString useBuCellServDB "cp ${buCellServDB}"}
306         '';
307         serviceConfig = {
308           ExecStart = "${openafsBin}/bin/bosserver -nofork";
309           ExecStop = "${openafsBin}/bin/bos shutdown localhost -wait -localauth";
310         };
311       };
312     };
313   };