|
41 | 41 | description = "The data directory for JoinMarket."; |
42 | 42 | }; |
43 | 43 | rpcWalletFile = mkOption { |
44 | | - type = types.nullOr types.str; |
| 44 | + type = types.nullOr types.nonEmptyStr; |
45 | 45 | default = "jm_wallet"; |
46 | 46 | description = '' |
47 | 47 | Name of the watch-only bitcoind wallet the JoinMarket addresses are imported to. |
48 | 48 | ''; |
49 | 49 | }; |
| 50 | + settings = mkOption { |
| 51 | + type = with types; attrsOf anything; |
| 52 | + example = { |
| 53 | + POLICY = { |
| 54 | + merge_algorithm = "gradual"; |
| 55 | + tx_fees = 5; |
| 56 | + }; |
| 57 | + LOGGING = { |
| 58 | + console_log_level = "DEBUG"; |
| 59 | + }; |
| 60 | + }; |
| 61 | + description = '' |
| 62 | + Joinmarket settings. |
| 63 | + See here for possible options: |
| 64 | + https://raw.githubusercontent.com/JoinMarket-Org/joinmarket-clientserver/master/src/jmclient/configure.py#:~:text=defaultconfig%20= |
| 65 | + If your web browser does not support text fragment URLs, you can can manually |
| 66 | + search for string `defaultconfig =` to jump to the correct location. |
| 67 | + ''; |
| 68 | + }; |
50 | 69 | user = mkOption { |
51 | 70 | type = types.str; |
52 | 71 | default = "joinmarket"; |
|
61 | 80 | default = cli; |
62 | 81 | defaultText = "(See source)"; |
63 | 82 | }; |
64 | | - # Used by ./joinmarket-ob-watcher.nix |
65 | | - messagingConfig = mkOption { |
66 | | - readOnly = true; |
67 | | - default = messagingConfig; |
68 | | - defaultText = "(See source)"; |
69 | | - }; |
70 | 83 | # This option is only used by netns-isolation. |
71 | 84 | # Tor is always enabled. |
72 | 85 | tor.enforce = nbLib.tor.enforce; |
@@ -142,88 +155,12 @@ let |
142 | 155 | inherit (config.services) bitcoind; |
143 | 156 |
|
144 | 157 | torAddress = config.services.tor.client.socksListenAddress; |
145 | | - socks5Settings = '' |
146 | | - socks5 = true |
147 | | - socks5_host = ${torAddress.addr} |
148 | | - socks5_port = ${toString torAddress.port} |
149 | | - ''; |
150 | | - |
151 | | - messagingConfig = '' |
152 | | - [MESSAGING:onion] |
153 | | - type = onion |
154 | | - ${socks5Settings} |
155 | | - tor_control_host = unix:/run/tor/control |
156 | | - # required option, but ignored for unix socket host |
157 | | - tor_control_port = 9051 |
158 | | - onion_serving_host = ${cfg.messagingAddress} |
159 | | - onion_serving_port = ${toString cfg.messagingPort} |
160 | | - hidden_service_dir = |
161 | | - directory_nodes = g3hv4uynnmynqqq2mchf3fcm3yd46kfzmcdogejuckgwknwyq5ya6iad.onion:5222,3kxw6lf5vf6y26emzwgibzhrzhmhqiw6ekrek3nqfjjmhwznb2moonad.onion:5222,bqlpq6ak24mwvuixixitift4yu42nxchlilrcqwk2ugn45tdclg42qid.onion:5222 |
162 | | -
|
163 | | - # irc.darkscience.net |
164 | | - [MESSAGING:server1] |
165 | | - host = darkirc6tqgpnwd3blln3yfv5ckl47eg7llfxkmtovrv7c7iwohhb6ad.onion |
166 | | - channel = joinmarket-pit |
167 | | - port = 6697 |
168 | | - usessl = true |
169 | | - ${socks5Settings} |
170 | | -
|
171 | | - # ilita |
172 | | - [MESSAGING:server2] |
173 | | - host = ilitafrzzgxymv6umx2ux7kbz3imyeko6cnqkvy4nisjjj4qpqkrptid.onion |
174 | | - channel = joinmarket-pit |
175 | | - port = 6667 |
176 | | - usessl = false |
177 | | - ${socks5Settings} |
178 | | -
|
179 | | - # irc.hackint.org |
180 | | - [MESSAGING:server3] |
181 | | - host = ncwkrwxpq2ikcngxq3dy2xctuheniggtqeibvgofixpzvrwpa77tozqd.onion |
182 | | - channel = joinmarket-pit |
183 | | - port = 6667 |
184 | | - usessl = false |
185 | | - ${socks5Settings} |
186 | | - ''; |
187 | | - |
188 | | - # Based on https://github.com/JoinMarket-Org/joinmarket-clientserver/blob/master/jmclient/jmclient/configure.py |
189 | | - yg = cfg.yieldgenerator; |
190 | | - configFile = builtins.toFile "config" '' |
191 | | - [DAEMON] |
192 | | - no_daemon = 0 |
193 | | - daemon_port = 27183 |
194 | | - daemon_host = 127.0.0.1 |
195 | | -
|
196 | | - [BLOCKCHAIN] |
197 | | - blockchain_source = ${bitcoind.makeNetworkName "bitcoin-rpc" "regtest"} |
198 | | - network = ${bitcoind.makeNetworkName "mainnet" "testnet"} |
199 | | - rpc_host = ${nbLib.address bitcoind.rpc.address} |
200 | | - rpc_port = ${toString bitcoind.rpc.port} |
201 | | - rpc_user = ${bitcoind.rpc.users.privileged.name} |
202 | | - ${optionalString (cfg.rpcWalletFile != null) "rpc_wallet_file = ${cfg.rpcWalletFile}"} |
203 | | -
|
204 | | - ${messagingConfig} |
205 | | -
|
206 | | - [LOGGING] |
207 | | - color = false |
208 | | -
|
209 | | - [PAYJOIN] |
210 | | - onion_socks5_host = ${torAddress.addr} |
211 | | - onion_socks5_port = ${toString torAddress.port} |
212 | | - tor_control_host = unix:/run/tor/control |
213 | | - onion_serving_host = ${cfg.payjoinAddress} |
214 | | - onion_serving_port = ${toString cfg.payjoinPort} |
215 | | - hidden_service_ssl = false |
216 | 158 |
|
217 | | - [YIELDGENERATOR] |
218 | | - ordertype = ${yg.ordertype} |
219 | | - cjfee_a = ${toString yg.cjfee_a} |
220 | | - cjfee_r = ${toString yg.cjfee_r} |
221 | | - cjfee_factor = ${toString yg.cjfee_factor} |
222 | | - txfee_contribution = 0 |
223 | | - txfee_contribution_factor = ${toString yg.txfee_contribution_factor} |
224 | | - minsize = ${toString yg.minsize} |
225 | | - size_factor = ${toString yg.size_factor} |
226 | | - ''; |
| 159 | + socks5Settings = { |
| 160 | + socks5 = true; |
| 161 | + socks5_host = torAddress.addr; |
| 162 | + socks5_port = torAddress.port; |
| 163 | + }; |
227 | 164 |
|
228 | 165 | # The jm scripts create a 'logs' dir in the working dir, |
229 | 166 | # so run them inside dataDir. |
|
242 | 179 | in { |
243 | 180 | inherit options; |
244 | 181 |
|
245 | | - config = mkIf cfg.enable (mkMerge [{ |
| 182 | + config = mkMerge [ |
| 183 | + { |
| 184 | + services.joinmarket.settings = { |
| 185 | + DAEMON = { |
| 186 | + no_daemon = 0; |
| 187 | + daemon_port = 27183; |
| 188 | + daemon_host = "127.0.0.1"; |
| 189 | + }; |
| 190 | + BLOCKCHAIN = { |
| 191 | + blockchain_source = bitcoind.makeNetworkName "bitcoin-rpc" "regtest"; |
| 192 | + network = bitcoind.makeNetworkName "mainnet" "testnet"; |
| 193 | + rpc_host = nbLib.address bitcoind.rpc.address; |
| 194 | + rpc_port = bitcoind.rpc.port; |
| 195 | + rpc_user = bitcoind.rpc.users.privileged.name; |
| 196 | + rpc_wallet_file = if cfg.rpcWalletFile == null then "" else cfg.rpcWalletFile; |
| 197 | + }; |
| 198 | + LOGGING = { |
| 199 | + color = false; |
| 200 | + }; |
| 201 | + PAYJOIN = { |
| 202 | + onion_socks5_host = torAddress.addr; |
| 203 | + onion_socks5_port = torAddress.port; |
| 204 | + tor_control_host = "unix:/run/tor/control"; |
| 205 | + onion_serving_host = cfg.payjoinAddress; |
| 206 | + onion_serving_port = cfg.payjoinPort; |
| 207 | + hidden_service_ssl = false; |
| 208 | + }; |
| 209 | + YIELDGENERATOR = removeAttrs cfg.yieldgenerator [ |
| 210 | + "enable" |
| 211 | + # TODO: This is only needed when ./obsolete-options.nix is imported |
| 212 | + "txfee" |
| 213 | + ]; |
| 214 | + |
| 215 | + # Messaging settings have to be fully specified because joinmarket doesn't |
| 216 | + # provide default messaging settings. |
| 217 | + # (`jmclient/configure.py` actually does contain default messaging settings, but |
| 218 | + # they are removed via fn `_remove_unwanted_default_settings`) |
| 219 | + "MESSAGING:onion" = socks5Settings // { |
| 220 | + type = "onion"; |
| 221 | + tor_control_host = "unix:/run/tor/control"; |
| 222 | + # Required option, but ignored because `tor_control_host` is a unix socket |
| 223 | + tor_control_port = 9051; |
| 224 | + onion_serving_host = cfg.messagingAddress; |
| 225 | + onion_serving_port = cfg.messagingPort; |
| 226 | + hidden_service_dir = ""; |
| 227 | + directory_nodes = "g3hv4uynnmynqqq2mchf3fcm3yd46kfzmcdogejuckgwknwyq5ya6iad.onion:5222,3kxw6lf5vf6y26emzwgibzhrzhmhqiw6ekrek3nqfjjmhwznb2moonad.onion:5222,bqlpq6ak24mwvuixixitift4yu42nxchlilrcqwk2ugn45tdclg42qid.onion:5222"; |
| 228 | + }; |
| 229 | + # irc.darkscience.net |
| 230 | + "MESSAGING:server1" = socks5Settings // { |
| 231 | + host = "darkirc6tqgpnwd3blln3yfv5ckl47eg7llfxkmtovrv7c7iwohhb6ad.onion"; |
| 232 | + channel = "joinmarket-pit"; |
| 233 | + port = 6697; |
| 234 | + usessl = true; |
| 235 | + }; |
| 236 | + # ilita |
| 237 | + "MESSAGING:server2" = socks5Settings // { |
| 238 | + host = "ilitafrzzgxymv6umx2ux7kbz3imyeko6cnqkvy4nisjjj4qpqkrptid.onion"; |
| 239 | + channel = "joinmarket-pit"; |
| 240 | + port = 6667; |
| 241 | + usessl = false; |
| 242 | + }; |
| 243 | + # irc.hackint.org |
| 244 | + "MESSAGING:server3" = socks5Settings // { |
| 245 | + host = "ncwkrwxpq2ikcngxq3dy2xctuheniggtqeibvgofixpzvrwpa77tozqd.onion"; |
| 246 | + channel = "joinmarket-pit"; |
| 247 | + port = 6667; |
| 248 | + usessl = false; |
| 249 | + }; |
| 250 | + }; |
| 251 | + } |
| 252 | + |
| 253 | + (mkIf cfg.enable { |
246 | 254 | services.bitcoind = { |
247 | 255 | enable = true; |
248 | 256 | disablewallet = false; |
|
275 | 283 | after = [ "bitcoind.service" "nix-bitcoin-secrets.target" ]; |
276 | 284 | preStart = '' |
277 | 285 | { |
278 | | - cat ${configFile} |
| 286 | + cat ${builtins.toFile "joinmarket.cfg" ((generators.toINI {}) cfg.settings)} |
279 | 287 | echo |
280 | 288 | echo '[BLOCKCHAIN]' |
281 | 289 | echo "rpc_password = $(cat ${secretsDir}/bitcoin-rpcpassword-privileged)" |
|
350 | 358 | nix-bitcoin.generateSecretsCmds.joinmarket = '' |
351 | 359 | makePasswordSecret jm-wallet-password |
352 | 360 | ''; |
353 | | - } |
| 361 | + }) |
354 | 362 |
|
355 | | - (mkIf cfg.yieldgenerator.enable { |
| 363 | + (mkIf (cfg.enable && cfg.yieldgenerator.enable) { |
356 | 364 | systemd.services.joinmarket-yieldgenerator = { |
357 | 365 | wantedBy = [ "joinmarket.service" ]; |
358 | 366 | requires = [ "joinmarket.service" ]; |
|
373 | 381 | } // nbLib.allowTor; |
374 | 382 | }; |
375 | 383 | }) |
376 | | - ]); |
| 384 | + ]; |
377 | 385 | } |
0 commit comments