]> git.immae.eu Git - perso/Immae/Config/Nix.git/blame - modules/private/databases/redis_replication.nix
Use attrs for secrets instead of lists
[perso/Immae/Config/Nix.git] / modules / private / databases / redis_replication.nix
CommitLineData
ab8f306d 1{ pkgs, config, lib, ... }:
dded6699
IB
2let
3 cfg = config.myServices.databasesReplication.redis;
4in
5{
6 options.myServices.databasesReplication.redis = {
7 enable = lib.mkEnableOption "Enable redis replication";
8 base = lib.mkOption {
9 type = lib.types.path;
10 description = ''
11 Base path to put the replications
12 '';
13 };
14 hosts = lib.mkOption {
15 default = {};
16 description = ''
17 Hosts to backup
18 '';
19 type = lib.types.attrsOf (lib.types.submodule {
20 options = {
21 package = lib.mkOption {
22 type = lib.types.package;
23 default = pkgs.redis;
24 description = ''
25 Redis package for this host
26 '';
27 };
28 host = lib.mkOption {
29 type = lib.types.str;
30 description = ''
31 Host to connect to
32 '';
33 };
34 port = lib.mkOption {
35 type = lib.types.str;
36 description = ''
37 Port to connect to
38 '';
39 };
40 password = lib.mkOption {
41 type = lib.types.nullOr lib.types.str;
42 default = null;
43 description = ''
44 Password to use
45 '';
46 };
47 };
48 });
49 };
50 };
51
52 config = lib.mkIf cfg.enable {
53 users.users.redis = {
54 description = "Redis database user";
55 group = "redis";
56 uid = config.ids.uids.redis;
57 extraGroups = [ "keys" ];
58 };
59 users.groups.redis.gid = config.ids.gids.redis;
60
61 services.spiped = { # sync from eldiron
62 enable = true;
63 config.redis = {
64 encrypt = true;
65 source = "127.0.0.1:16379";
ab8f306d 66 target = "${config.myEnv.servers.eldiron.ips.main.ip4}:16379";
da30ae4f 67 keyfile = config.secrets.fullPaths."redis/spiped_eldiron_keyfile";
dded6699
IB
68 };
69 };
70
4c4652aa
IB
71 secrets.keys = lib.mapAttrs' (name: hcfg:
72 lib.nameValuePair "redis_replication/${name}/config" {
dded6699
IB
73 user = "redis";
74 group = "redis";
75 permissions = "0400";
76 text = ''
77 pidfile ${cfg.base}/${name}/redis/redis.pid
78 port 0
79 unixsocket /run/redis_${name}/redis.sock
80 loglevel notice
81 logfile /dev/null
82 syslog-enabled yes
83 databases 16
84 save 900 1
85 save 300 10
86 save 60 10000
87 dbfilename dump.rdb
88 dir ${cfg.base}/${name}/redis/
89 slaveof ${hcfg.host} ${hcfg.port}
90 ${if hcfg.password != null then "masterauth ${hcfg.password}" else ""}
91 appendOnly no
92 appendfsync everysec
93 slowlog-log-slower-than 10000
94 slowlog-max-len 128
95 unixsocketperm 777
96 maxclients 1024
97 '';
98 }
4c4652aa
IB
99 ) cfg.hosts // {
100 "redis/spiped_eldiron_keyfile" = { # For eldiron only
dded6699
IB
101 user = "spiped";
102 group = "spiped";
103 permissions = "0400";
ab8f306d 104 text = config.myEnv.databases.redis.spiped_key;
4c4652aa
IB
105 };
106 };
dded6699
IB
107
108 services.cron = {
109 enable = true;
110 systemCronJobs = lib.flatten (lib.mapAttrsToList (name: hcfg:
111 let
112 dataDir = "${cfg.base}/${name}/redis";
113 backupDir = "${cfg.base}/${name}/redis_backup";
114 backup_script = pkgs.writeScript "backup_redis_${name}" ''
115 #!${pkgs.stdenv.shell}
116
117 ${pkgs.coreutils}/bin/cp ${cfg.base}/${name}/redis/dump.rdb \
4c853ba6 118 ${backupDir}/$(${pkgs.coreutils}/bin/date -Iminutes).rdb
dded6699
IB
119 '';
120 u = pkgs.callPackage ./utils.nix {};
121 cleanup_script = pkgs.writeScript "cleanup_redis_${name}" (u.exponentialDumps "rdb" backupDir);
122 in [
123 "0 22,4,10,16 * * * root ${backup_script}"
124 "0 3 * * * root ${cleanup_script}"
125 ]) cfg.hosts);
126 };
127
128 system.activationScripts = lib.attrsets.mapAttrs' (name: hcfg:
129 lib.attrsets.nameValuePair "redis_replication_${name}" {
130 deps = [ "users" "groups" ];
131 text = ''
132 install -m 0700 -o redis -g redis -d ${cfg.base}/${name}/redis
133 install -m 0700 -o redis -g redis -d ${cfg.base}/${name}/redis_backup
134 '';
135 }) cfg.hosts;
136
137 systemd.services = {
138 spiped_redis = { # For eldiron
139 description = "Secure pipe 'redis'";
140 after = [ "network.target" ];
141 wantedBy = [ "multi-user.target" ];
142
143 serviceConfig = {
144 Restart = "always";
145 User = "spiped";
146 PermissionsStartOnly = true;
147 SupplementaryGroups = "keys";
148 };
149
150 script = "exec ${pkgs.spiped}/bin/spiped -F `cat /etc/spiped/redis.spec`";
151 };
152 } // lib.attrsets.mapAttrs' (name: hcfg:
153 let
154 dataDir = "${cfg.base}/${name}/redis";
155 in
156 lib.attrsets.nameValuePair "redis_backup_${name}" {
157 description = "Redis replication for ${name}";
158 wantedBy = [ "multi-user.target" ];
159 after = [ "network.target" ];
160 unitConfig.RequiresMountsFor = dataDir;
161
162 serviceConfig = {
da30ae4f 163 ExecStart = "${hcfg.package}/bin/redis-server ${config.secrets.fullPaths."redis_replication/${name}/config"}";
dded6699
IB
164 User = "redis";
165 RuntimeDirectory = "redis_${name}";
166 };
167 }) cfg.hosts;
168 };
169}
170
171