|
29 | 29 |
|
30 | 30 | configFile = pkgs.writeText "shadowsocks.json" (builtins.toJSON opts); |
31 | 31 |
|
| 32 | + executablesMap = { |
| 33 | + "${getName pkgs.shadowsocks-libev}" = { |
| 34 | + server = "ss-server"; |
| 35 | + }; |
| 36 | + "${getName pkgs.shadowsocks-rust}" = { |
| 37 | + server = "ssserver"; |
| 38 | + }; |
| 39 | + }; |
32 | 40 | in |
33 | | - |
34 | 41 | { |
35 | 42 |
|
36 | 43 | ###### interface |
|
47 | 54 | ''; |
48 | 55 | }; |
49 | 56 |
|
| 57 | + package = mkPackageOption pkgs "Shadowsocks" { |
| 58 | + default = "shadowsocks-libev"; |
| 59 | + }; |
| 60 | + |
50 | 61 | localAddress = mkOption { |
51 | | - type = types.coercedTo types.str singleton (types.listOf types.str); |
| 62 | + type = |
| 63 | + with types; |
| 64 | + oneOf [ |
| 65 | + str |
| 66 | + (listOf str) |
| 67 | + ]; |
| 68 | + # Keeped for compatibility |
52 | 69 | default = [ |
53 | 70 | "[::0]" |
54 | 71 | "0.0.0.0" |
55 | 72 | ]; |
56 | 73 | description = '' |
57 | 74 | Local addresses to which the server binds. |
| 75 | + Note: shadowsocks-rust accepts only string parameter. |
58 | 76 | ''; |
59 | 77 | }; |
60 | 78 |
|
|
163 | 181 | (noPasswd && !noPasswdFile) || (!noPasswd && noPasswdFile); |
164 | 182 | message = "Option `password` or `passwordFile` must be set and cannot be set simultaneously"; |
165 | 183 | } |
| 184 | + { |
| 185 | + # Ensure localAddress is a string if package is shadowsocks-rust |
| 186 | + assertion = !(getName cfg.package == "shadowsocks-rust" && !lib.strings.isString cfg.localAddress); |
| 187 | + message = "Option `localAddress` must be a string when using shadowsocks-rust."; |
| 188 | + } |
166 | 189 | ]; |
167 | 190 |
|
168 | | - systemd.services.shadowsocks-libev = { |
169 | | - description = "shadowsocks-libev Daemon"; |
| 191 | + systemd.services.${getName cfg.package} = { |
| 192 | + description = "${getName cfg.package} Daemon"; |
170 | 193 | after = [ "network.target" ]; |
171 | 194 | wantedBy = [ "multi-user.target" ]; |
172 | 195 | path = [ |
173 | | - pkgs.shadowsocks-libev |
| 196 | + cfg.package |
174 | 197 | ] |
175 | 198 | ++ optional (cfg.plugin != null) cfg.plugin |
176 | 199 | ++ optional (cfg.passwordFile != null) pkgs.jq; |
|
179 | 202 | ${optionalString (cfg.passwordFile != null) '' |
180 | 203 | cat ${configFile} | jq --arg password "$(cat "${cfg.passwordFile}")" '. + { password: $password }' > /tmp/shadowsocks.json |
181 | 204 | ''} |
182 | | - exec ss-server -c ${if cfg.passwordFile != null then "/tmp/shadowsocks.json" else configFile} |
| 205 | + exec ${(executablesMap.${getName cfg.package}).server} -c ${ |
| 206 | + if cfg.passwordFile != null then "/tmp/shadowsocks.json" else configFile |
| 207 | + } |
183 | 208 | ''; |
184 | 209 | }; |
185 | 210 | }; |
|
0 commit comments