confctl 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (130) hide show
  1. checksums.yaml +7 -0
  2. data/.editorconfig +11 -0
  3. data/.gitignore +8 -0
  4. data/.overcommit.yml +6 -0
  5. data/.rubocop.yml +67 -0
  6. data/.rubocop_todo.yml +5 -0
  7. data/.ruby-version +1 -0
  8. data/CHANGELOG.md +2 -0
  9. data/Gemfile +2 -0
  10. data/LICENSE.txt +674 -0
  11. data/README.md +522 -0
  12. data/Rakefile +40 -0
  13. data/bin/confctl +4 -0
  14. data/confctl.gemspec +33 -0
  15. data/example/.gitignore +2 -0
  16. data/example/README.md +38 -0
  17. data/example/cluster/cluster.nix +7 -0
  18. data/example/cluster/module-list.nix +3 -0
  19. data/example/cluster/nixos-machine/config.nix +15 -0
  20. data/example/cluster/nixos-machine/hardware.nix +4 -0
  21. data/example/cluster/nixos-machine/module.nix +8 -0
  22. data/example/cluster/vpsadminos-container/config.nix +22 -0
  23. data/example/cluster/vpsadminos-container/module.nix +8 -0
  24. data/example/cluster/vpsadminos-machine/config.nix +22 -0
  25. data/example/cluster/vpsadminos-machine/hardware.nix +4 -0
  26. data/example/cluster/vpsadminos-machine/module.nix +8 -0
  27. data/example/cluster/vpsfreecz-vps/config.nix +25 -0
  28. data/example/cluster/vpsfreecz-vps/module.nix +8 -0
  29. data/example/configs/confctl.nix +10 -0
  30. data/example/configs/swpins.nix +28 -0
  31. data/example/data/default.nix +5 -0
  32. data/example/data/ssh-keys.nix +7 -0
  33. data/example/environments/base.nix +13 -0
  34. data/example/modules/module-list.nix +13 -0
  35. data/example/shell.nix +11 -0
  36. data/example/swpins/channels/nixos-unstable.json +35 -0
  37. data/example/swpins/channels/vpsadminos-staging.json +35 -0
  38. data/lib/confctl/cli/app.rb +551 -0
  39. data/lib/confctl/cli/attr_filters.rb +51 -0
  40. data/lib/confctl/cli/cluster.rb +1248 -0
  41. data/lib/confctl/cli/command.rb +206 -0
  42. data/lib/confctl/cli/configuration.rb +296 -0
  43. data/lib/confctl/cli/gen_data.rb +97 -0
  44. data/lib/confctl/cli/generation.rb +335 -0
  45. data/lib/confctl/cli/log_view.rb +267 -0
  46. data/lib/confctl/cli/output_formatter.rb +288 -0
  47. data/lib/confctl/cli/swpins/base.rb +40 -0
  48. data/lib/confctl/cli/swpins/channel.rb +73 -0
  49. data/lib/confctl/cli/swpins/cluster.rb +80 -0
  50. data/lib/confctl/cli/swpins/core.rb +86 -0
  51. data/lib/confctl/cli/swpins/utils.rb +55 -0
  52. data/lib/confctl/cli/swpins.rb +5 -0
  53. data/lib/confctl/cli/tag_filters.rb +30 -0
  54. data/lib/confctl/cli.rb +5 -0
  55. data/lib/confctl/conf_cache.rb +105 -0
  56. data/lib/confctl/conf_dir.rb +88 -0
  57. data/lib/confctl/erb_template.rb +37 -0
  58. data/lib/confctl/exceptions.rb +3 -0
  59. data/lib/confctl/gcroot.rb +30 -0
  60. data/lib/confctl/generation/build.rb +145 -0
  61. data/lib/confctl/generation/build_list.rb +106 -0
  62. data/lib/confctl/generation/host.rb +35 -0
  63. data/lib/confctl/generation/host_list.rb +81 -0
  64. data/lib/confctl/generation/unified.rb +117 -0
  65. data/lib/confctl/generation/unified_list.rb +63 -0
  66. data/lib/confctl/git_repo_mirror.rb +79 -0
  67. data/lib/confctl/health_checks/base.rb +66 -0
  68. data/lib/confctl/health_checks/run_command.rb +179 -0
  69. data/lib/confctl/health_checks/systemd/properties.rb +84 -0
  70. data/lib/confctl/health_checks/systemd/property_check.rb +31 -0
  71. data/lib/confctl/health_checks/systemd/property_list.rb +20 -0
  72. data/lib/confctl/health_checks.rb +5 -0
  73. data/lib/confctl/hook.rb +35 -0
  74. data/lib/confctl/line_buffer.rb +53 -0
  75. data/lib/confctl/logger.rb +151 -0
  76. data/lib/confctl/machine.rb +107 -0
  77. data/lib/confctl/machine_control.rb +172 -0
  78. data/lib/confctl/machine_list.rb +108 -0
  79. data/lib/confctl/machine_status.rb +135 -0
  80. data/lib/confctl/module_options.rb +95 -0
  81. data/lib/confctl/nix.rb +382 -0
  82. data/lib/confctl/nix_build.rb +108 -0
  83. data/lib/confctl/nix_collect_garbage.rb +64 -0
  84. data/lib/confctl/nix_copy.rb +49 -0
  85. data/lib/confctl/nix_format.rb +124 -0
  86. data/lib/confctl/nix_literal_expression.rb +15 -0
  87. data/lib/confctl/parallel_executor.rb +43 -0
  88. data/lib/confctl/pattern.rb +9 -0
  89. data/lib/confctl/settings.rb +50 -0
  90. data/lib/confctl/std_line_buffer.rb +40 -0
  91. data/lib/confctl/swpins/change_set.rb +151 -0
  92. data/lib/confctl/swpins/channel.rb +62 -0
  93. data/lib/confctl/swpins/channel_list.rb +47 -0
  94. data/lib/confctl/swpins/cluster_name.rb +94 -0
  95. data/lib/confctl/swpins/cluster_name_list.rb +15 -0
  96. data/lib/confctl/swpins/core.rb +137 -0
  97. data/lib/confctl/swpins/deployed_info.rb +23 -0
  98. data/lib/confctl/swpins/spec.rb +20 -0
  99. data/lib/confctl/swpins/specs/base.rb +184 -0
  100. data/lib/confctl/swpins/specs/directory.rb +51 -0
  101. data/lib/confctl/swpins/specs/git.rb +135 -0
  102. data/lib/confctl/swpins/specs/git_rev.rb +24 -0
  103. data/lib/confctl/swpins.rb +17 -0
  104. data/lib/confctl/system_command.rb +10 -0
  105. data/lib/confctl/user_script.rb +13 -0
  106. data/lib/confctl/user_scripts.rb +41 -0
  107. data/lib/confctl/utils/file.rb +21 -0
  108. data/lib/confctl/version.rb +3 -0
  109. data/lib/confctl.rb +43 -0
  110. data/man/man8/confctl-options.nix.8 +1334 -0
  111. data/man/man8/confctl-options.nix.8.md +1340 -0
  112. data/man/man8/confctl.8 +660 -0
  113. data/man/man8/confctl.8.md +654 -0
  114. data/nix/evaluator.nix +160 -0
  115. data/nix/lib/default.nix +83 -0
  116. data/nix/lib/machine/default.nix +74 -0
  117. data/nix/lib/machine/info.nix +5 -0
  118. data/nix/lib/swpins/eval.nix +71 -0
  119. data/nix/lib/swpins/options.nix +94 -0
  120. data/nix/machines.nix +31 -0
  121. data/nix/modules/cluster/default.nix +459 -0
  122. data/nix/modules/confctl/cli.nix +21 -0
  123. data/nix/modules/confctl/generations.nix +84 -0
  124. data/nix/modules/confctl/nix.nix +28 -0
  125. data/nix/modules/confctl/swpins.nix +55 -0
  126. data/nix/modules/module-list.nix +19 -0
  127. data/shell.nix +42 -0
  128. data/template/confctl-options.nix/main.erb +45 -0
  129. data/template/confctl-options.nix/options.erb +15 -0
  130. metadata +353 -0
@@ -0,0 +1,459 @@
1
+ { config, lib, confLib, ... }@args:
2
+ with lib;
3
+ let
4
+ machine =
5
+ { config, ...}:
6
+ {
7
+ options = {
8
+ managed = mkOption {
9
+ type = types.nullOr types.bool;
10
+ default = null;
11
+ apply = v:
12
+ if !isNull v then v
13
+ else if elem config.spin [ "nixos" "vpsadminos" ] then true
14
+ else false;
15
+ description = ''
16
+ Determines whether the machine is managed using confctl or not
17
+
18
+ By default, NixOS and vpsAdminOS machines are managed by confctl.
19
+ '';
20
+ };
21
+
22
+ spin = mkOption {
23
+ type = types.enum [ "openvz" "nixos" "vpsadminos" "other" ];
24
+ description = "OS type";
25
+ };
26
+
27
+ swpins = {
28
+ channels = mkOption {
29
+ type = types.listOf types.str;
30
+ default = [];
31
+ description = ''
32
+ List of channels from <option>confctl.swpins.channels</option>
33
+ to use on this machine
34
+ '';
35
+ };
36
+
37
+ pins = mkOption {
38
+ type = types.attrsOf (types.submodule swpinOptions.specModule);
39
+ default = {};
40
+ description = ''
41
+ List of swpins for this machine, which can supplement or
42
+ override swpins from configured channels
43
+ '';
44
+ };
45
+ };
46
+
47
+ addresses = mkOption {
48
+ type = types.nullOr (types.submodule addresses);
49
+ default = null;
50
+ description = ''
51
+ IP addresses
52
+ '';
53
+ };
54
+
55
+ netboot = {
56
+ enable = mkEnableOption "Include this system on pxe servers";
57
+ macs = mkOption {
58
+ type = types.listOf types.str;
59
+ default = [];
60
+ description = ''
61
+ List of MAC addresses for iPXE node auto-detection
62
+ '';
63
+ };
64
+ };
65
+
66
+ host = mkOption {
67
+ type = types.nullOr (types.submodule host);
68
+ default = null;
69
+ };
70
+
71
+ labels = mkOption {
72
+ type = types.attrs;
73
+ default = {};
74
+ description = ''
75
+ Optional user-defined labels to classify the machine
76
+ '';
77
+ };
78
+
79
+ tags = mkOption {
80
+ type = types.listOf types.str;
81
+ default = [];
82
+ description = ''
83
+ Optional user-defined tags to classify the machine
84
+ '';
85
+ };
86
+
87
+ nix = {
88
+ nixPath = mkOption {
89
+ type = types.listOf types.str;
90
+ default = [];
91
+ description = ''
92
+ List of extra paths added to environment variable
93
+ <literal>NIX_PATH</literal> for <literal>nix-build</literal>
94
+ '';
95
+ };
96
+ };
97
+
98
+ buildGenerations = {
99
+ min = mkOption {
100
+ type = types.nullOr types.int;
101
+ default = null;
102
+ description = ''
103
+ The minimum number of build generations to be kept on the build
104
+ machine.
105
+ '';
106
+ };
107
+
108
+ max = mkOption {
109
+ type = types.nullOr types.int;
110
+ default = null;
111
+ description = ''
112
+ The maximum number of build generations to be kept on the build
113
+ machine.
114
+ '';
115
+ };
116
+
117
+ maxAge = mkOption {
118
+ type = types.nullOr types.int;
119
+ default = null;
120
+ description = ''
121
+ Delete build generations older than
122
+ <option>cluster.&lt;name&gt;.buildGenerations.maxAge</option>
123
+ seconds from the build machine. Old generations are deleted even
124
+ if <option>cluster.&lt;name&gt;.buildGenerations.max</option> is
125
+ not reached.
126
+ '';
127
+ };
128
+ };
129
+
130
+ hostGenerations = {
131
+ min = mkOption {
132
+ type = types.nullOr types.int;
133
+ default = null;
134
+ description = ''
135
+ The minimum number of generations to be kept on the machine.
136
+ '';
137
+ };
138
+
139
+ max = mkOption {
140
+ type = types.nullOr types.int;
141
+ default = null;
142
+ description = ''
143
+ The maximum number of generations to be kept on the machine.
144
+ '';
145
+ };
146
+
147
+ maxAge = mkOption {
148
+ type = types.nullOr types.int;
149
+ default = null;
150
+ description = ''
151
+ Delete generations older than
152
+ <option>cluster.&lt;name&gt;.hostGenerations.maxAge</option>
153
+ seconds from the machine. Old generations are deleted even
154
+ if <option>cluster.&lt;name&gt;.hostGenerations.max</option> is
155
+ not reached.
156
+ '';
157
+ };
158
+
159
+ collectGarbage = mkOption {
160
+ type = types.nullOr types.bool;
161
+ default = null;
162
+ description = "Run nix-collect-garbage";
163
+ };
164
+ };
165
+
166
+ healthChecks = {
167
+ systemd = {
168
+ enable = mkOption {
169
+ type = types.bool;
170
+ default = true;
171
+ description = ''
172
+ Enable systemd checks, enabled by default
173
+ '';
174
+ };
175
+
176
+ systemProperties = mkOption {
177
+ type = types.listOf (types.submodule systemdProperty);
178
+ default = [
179
+ { property = "SystemState"; value = "running"; }
180
+ ];
181
+ description = ''
182
+ Check systemd manager properties reported by systemctl show
183
+ '';
184
+ };
185
+
186
+ unitProperties = mkOption {
187
+ type = types.attrsOf (types.listOf (types.submodule systemdProperty));
188
+ default = {};
189
+ example = literalExpression ''
190
+ {
191
+ "firewall.service" = [
192
+ { property = "ActiveState"; value = "active"; }
193
+ ];
194
+ }
195
+ '';
196
+ description = ''
197
+ Check systemd unit properties reported by systemctl show <unit>
198
+ '';
199
+ };
200
+ };
201
+
202
+ builderCommands = mkOption {
203
+ type = types.listOf (types.submodule checkCommand);
204
+ default = [];
205
+ example = literalExpression ''
206
+ [
207
+ { description = "ping"; command = [ "ping" "-c1" "{host.fqdn}" ]; }
208
+ ]
209
+ '';
210
+ description = ''
211
+ Check commands run on the build machine
212
+ '';
213
+ };
214
+
215
+ machineCommands = mkOption {
216
+ type = types.listOf (types.submodule checkCommand);
217
+ default = [];
218
+ example = literalExpression ''
219
+ [
220
+ { description = "curl"; command = [ "curl" "-s" "http://localhost:80" ]; }
221
+ ]
222
+ '';
223
+ description = ''
224
+ Check commands run on the target machine
225
+
226
+ Note that the commands have to be available on the machine.
227
+ '';
228
+ };
229
+ };
230
+ };
231
+ };
232
+
233
+ swpinOptions = import ../../lib/swpins/options.nix { inherit lib; };
234
+
235
+ addresses =
236
+ { config, ... }:
237
+ {
238
+ options = {
239
+ primary = mkOption {
240
+ type = types.nullOr (types.submodule (confLib.mkOptions.addresses 4));
241
+ default =
242
+ if config.v4 != [] then
243
+ head config.v4
244
+ else if config.v6 != [] then
245
+ head config.v6
246
+ else
247
+ null;
248
+ description = ''
249
+ Default address other machines should use to connect to this machine
250
+
251
+ Defaults to the first IPv4 address if not set
252
+ '';
253
+ };
254
+
255
+ v4 = mkOption {
256
+ type = types.listOf (types.submodule (confLib.mkOptions.addresses 4));
257
+ default = [];
258
+ description = ''
259
+ List of IPv4 addresses this machine responds to
260
+ '';
261
+ };
262
+
263
+ v6 = mkOption {
264
+ type = types.listOf (types.submodule (confLib.mkOptions.addresses 6));
265
+ default = [];
266
+ description = ''
267
+ List of IPv6 addresses this machine responds to
268
+ '';
269
+ };
270
+ };
271
+ };
272
+
273
+ host =
274
+ { config, ... }:
275
+ {
276
+ options = {
277
+ name = mkOption {
278
+ type = types.nullOr types.str;
279
+ default = null;
280
+ description = ''
281
+ Host name
282
+ '';
283
+ };
284
+
285
+ location = mkOption {
286
+ type = types.nullOr types.str;
287
+ default = null;
288
+ description = ''
289
+ Host location domain
290
+ '';
291
+ };
292
+
293
+ domain = mkOption {
294
+ type = types.nullOr types.str;
295
+ default = null;
296
+ description = ''
297
+ Host domain
298
+ '';
299
+ };
300
+
301
+ fullDomain = mkOption {
302
+ type = types.nullOr types.str;
303
+ default = null;
304
+ description = ''
305
+ Domain including location, i.e. FQDN without host name
306
+ '';
307
+ apply = v:
308
+ if isNull v && !isNull config.domain then
309
+ concatStringsSep "." (
310
+ (optional (!isNull config.location) config.location)
311
+ ++ [ config.domain ]
312
+ )
313
+ else
314
+ v;
315
+ };
316
+
317
+ fqdn = mkOption {
318
+ type = types.nullOr types.str;
319
+ default = null;
320
+ description = ''
321
+ Host FQDN
322
+ '';
323
+ apply = v:
324
+ if isNull v && !isNull config.name && !isNull config.domain then
325
+ concatStringsSep "." (
326
+ [ config.name ]
327
+ ++ (optional (!isNull config.location) config.location)
328
+ ++ [ config.domain ]
329
+ )
330
+ else
331
+ v;
332
+ };
333
+
334
+ target = mkOption {
335
+ type = types.nullOr types.str;
336
+ default = config.fqdn;
337
+ description = ''
338
+ Address/host to which the configuration is deployed to
339
+ '';
340
+ };
341
+ };
342
+ };
343
+
344
+ systemdProperty =
345
+ { config, ... }:
346
+ {
347
+ options = {
348
+ property = mkOption {
349
+ type = types.str;
350
+ description = "systemd property name";
351
+ };
352
+
353
+ value = mkOption {
354
+ type = types.str;
355
+ description = "value to be checked";
356
+ };
357
+
358
+ timeout = mkOption {
359
+ type = types.ints.unsigned;
360
+ default = 60;
361
+ description = "Max number of seconds to wait for the check to pass";
362
+ };
363
+
364
+ cooldown = mkOption {
365
+ type = types.ints.unsigned;
366
+ default = 3;
367
+ description = "Number of seconds in between check attempts";
368
+ };
369
+ };
370
+ };
371
+
372
+ checkCommand =
373
+ { config, ... }:
374
+ {
375
+ options = {
376
+ description = mkOption {
377
+ type = types.str;
378
+ default = "";
379
+ description = "Command description";
380
+ };
381
+
382
+ command = mkOption {
383
+ type = types.listOf types.str;
384
+ description = ''
385
+ Command and its arguments
386
+
387
+ It is possible to access machine attributes as from CLI using curly
388
+ brackets. For example, {host.fqdn} would be replaced by machine FQDN.
389
+ See confctl ls -L for a list of available attributes.
390
+ '';
391
+ };
392
+
393
+ exitStatus = mkOption {
394
+ type = types.ints.unsigned;
395
+ default = 0;
396
+ description = "Expected exit status";
397
+ };
398
+
399
+ standardOutput = {
400
+ match = mkOption {
401
+ type = types.nullOr types.str;
402
+ default = null;
403
+ description = "Standard output must match this string";
404
+ };
405
+
406
+ include = mkOption {
407
+ type = types.listOf types.str;
408
+ default = [];
409
+ description = "Strings that must be included in standard output";
410
+ };
411
+
412
+ exclude = mkOption {
413
+ type = types.listOf types.str;
414
+ default = [];
415
+ description = "Strings that must not be included in standard output";
416
+ };
417
+ };
418
+
419
+ standardError = {
420
+ match = mkOption {
421
+ type = types.nullOr types.str;
422
+ default = null;
423
+ description = "Standard error must match this string";
424
+ };
425
+
426
+ include = mkOption {
427
+ type = types.listOf types.str;
428
+ default = [];
429
+ description = "String that must be included in standard error";
430
+ };
431
+
432
+ exclude = mkOption {
433
+ type = types.listOf types.str;
434
+ default = [];
435
+ description = "String that must not be included in standard error";
436
+ };
437
+ };
438
+
439
+ timeout = mkOption {
440
+ type = types.ints.unsigned;
441
+ default = 60;
442
+ description = "Max number of seconds to wait for the check to pass";
443
+ };
444
+
445
+ cooldown = mkOption {
446
+ type = types.ints.unsigned;
447
+ default = 3;
448
+ description = "Number of seconds in between check attempts";
449
+ };
450
+ };
451
+ };
452
+ in {
453
+ options = {
454
+ cluster = mkOption {
455
+ type = types.attrsOf (types.submodule machine);
456
+ default = {};
457
+ };
458
+ };
459
+ }
@@ -0,0 +1,21 @@
1
+ { config, lib, ... }:
2
+ with lib;
3
+ {
4
+ options = {
5
+ confctl = {
6
+ list.columns = mkOption {
7
+ type = types.listOf types.str;
8
+ default = [
9
+ "name"
10
+ "spin"
11
+ "host.fqdn"
12
+ ];
13
+ description = ''
14
+ Configure which columns should <literal>confctl ls</literal> show.
15
+ Names correspond to options within <literal>cluster.&lt;name&gt;</literal>
16
+ module.
17
+ '';
18
+ };
19
+ };
20
+ };
21
+ }
@@ -0,0 +1,84 @@
1
+ { config, lib, ... }:
2
+ with lib;
3
+ {
4
+ options = {
5
+ confctl = {
6
+ buildGenerations = {
7
+ min = mkOption {
8
+ type = types.int;
9
+ default = 5;
10
+ description = ''
11
+ The minimum number of build generations to be kept.
12
+
13
+ This is the default value, which can be overriden per host.
14
+ '';
15
+ };
16
+
17
+ max = mkOption {
18
+ type = types.int;
19
+ default = 30;
20
+ description = ''
21
+ The maximum number of build generations to be kept.
22
+
23
+ This is the default value, which can be overriden per host.
24
+ '';
25
+ };
26
+
27
+ maxAge = mkOption {
28
+ type = types.int;
29
+ default = 180*24*60*60;
30
+ description = ''
31
+ Delete build generations older than
32
+ <option>confctl.buildGenerations.maxAge</option> seconds. Old generations
33
+ are deleted even if <option>confctl.buildGenerations.max</option> is
34
+ not reached.
35
+
36
+ This is the default value, which can be overriden per host.
37
+ '';
38
+ };
39
+ };
40
+
41
+ hostGenerations = {
42
+ min = mkOption {
43
+ type = types.int;
44
+ default = 5;
45
+ description = ''
46
+ The minimum number of generations to be kept on machines.
47
+
48
+ This is the default value, which can be overriden per host.
49
+ '';
50
+ };
51
+
52
+ max = mkOption {
53
+ type = types.int;
54
+ default = 30;
55
+ description = ''
56
+ The maximum number of generations to be kept on machines.
57
+
58
+ This is the default value, which can be overriden per host.
59
+ '';
60
+ };
61
+
62
+ maxAge = mkOption {
63
+ type = types.int;
64
+ default = 180*24*60*60;
65
+ description = ''
66
+ Delete generations older than
67
+ <option>confctl.hostGenerations.maxAge</option> seconds from
68
+ machines. Old generations
69
+ are deleted even if <option>confctl.hostGenerations.max</option> is
70
+ not reached.
71
+
72
+ This is the default value, which can be overriden per host.
73
+ '';
74
+ };
75
+
76
+ collectGarbage = mkOption {
77
+ type = types.bool;
78
+ default = true;
79
+ description = "Run nix-collect-garbage";
80
+ };
81
+ };
82
+ };
83
+ };
84
+ }
@@ -0,0 +1,28 @@
1
+ { config, lib, ... }:
2
+ with lib;
3
+ {
4
+ options = {
5
+ confctl = {
6
+ nix = {
7
+ maxJobs = mkOption {
8
+ type = types.nullOr (types.either types.int (types.enum [ "auto" ]));
9
+ default = null;
10
+ description = ''
11
+ Maximum number of build jobs, passed to <literal>nix-build</literal>
12
+ commands.
13
+ '';
14
+ };
15
+
16
+ nixPath = mkOption {
17
+ type = types.listOf types.str;
18
+ default = [];
19
+ description = ''
20
+ List of extra paths added to environment variable
21
+ <literal>NIX_PATH</literal> for all <literal>nix-build</literal>
22
+ invokations
23
+ '';
24
+ };
25
+ };
26
+ };
27
+ };
28
+ }
@@ -0,0 +1,55 @@
1
+ { config, pkgs, lib, swpinsInfo, ... }:
2
+ with lib;
3
+ let
4
+ swpinOptions = import ../../lib/swpins/options.nix { inherit lib; };
5
+
6
+ machineSwpinsInfo = pkgs.writeText "swpins-info.json" (builtins.toJSON swpinsInfo);
7
+ in {
8
+ options = {
9
+ confctl = {
10
+ swpins.core = {
11
+ pins = mkOption {
12
+ type = types.attrsOf (types.submodule swpinOptions.specModule);
13
+ default = {
14
+ nixpkgs = {
15
+ type = "git-rev";
16
+ git-rev = {
17
+ url = "https://github.com/NixOS/nixpkgs";
18
+ update.ref = "refs/heads/nixos-unstable";
19
+ update.auto = true;
20
+ update.interval = 30*24*60*60; # 1 month
21
+ };
22
+ };
23
+ };
24
+ description = ''
25
+ Core software packages used internally by confctl
26
+
27
+ It has to contain package <literal>nixpkgs</literal>, which is used
28
+ to resolve other software pins from channels or cluster machines.
29
+ '';
30
+ };
31
+
32
+ channels = mkOption {
33
+ type = types.listOf types.str;
34
+ default = [];
35
+ description = ''
36
+ List of channels from <option>confctl.swpins.channels</option>
37
+ to use for core swpins
38
+ '';
39
+ };
40
+ };
41
+
42
+ swpins.channels = mkOption {
43
+ type = types.attrsOf (types.attrsOf (types.submodule swpinOptions.specModule));
44
+ default = {};
45
+ description = ''
46
+ Software pin channels
47
+ '';
48
+ };
49
+ };
50
+ };
51
+
52
+ config = {
53
+ environment.etc."confctl/swpins-info.json".source = machineSwpinsInfo;
54
+ };
55
+ }
@@ -0,0 +1,19 @@
1
+ let
2
+ shared = [
3
+ ./cluster
4
+ ./confctl/generations.nix
5
+ ./confctl/cli.nix
6
+ ./confctl/nix.nix
7
+ ./confctl/swpins.nix
8
+ ];
9
+
10
+ nixos = [
11
+ ];
12
+
13
+ vpsadminos = [
14
+ ];
15
+ in {
16
+ nixos = shared ++ nixos;
17
+ vpsadminos = shared ++ vpsadminos;
18
+ all = shared ++ nixos ++ vpsadminos;
19
+ }
data/shell.nix ADDED
@@ -0,0 +1,42 @@
1
+ let
2
+ pkgs = import <nixpkgs> {};
3
+ lib = pkgs.lib;
4
+ stdenv = pkgs.stdenv;
5
+ in stdenv.mkDerivation rec {
6
+ name = "confctl-shell";
7
+
8
+ buildInputs = with pkgs; [
9
+ git
10
+ ncurses
11
+ nix-prefetch-git
12
+ openssl
13
+ ruby
14
+ ];
15
+
16
+ shellHook = ''
17
+ CONFCTL="${toString ./.}"
18
+ BASEDIR="$(realpath `pwd`)"
19
+ export GEM_HOME="$(pwd)/.gems"
20
+ BINDIR="$(ruby -e 'puts Gem.bindir')"
21
+ mkdir -p "$BINDIR"
22
+ export PATH="$BINDIR:$PATH"
23
+ export RUBYLIB="$GEM_HOME:$CONFCTL/lib"
24
+ export MANPATH="$CONFCTL/man:$(man --path)"
25
+ gem install --no-document bundler overcommit rubocop
26
+ pushd "$CONFCTL"
27
+ bundle install
28
+ bundle exec rake md2man:man
29
+ popd
30
+
31
+ cat <<EOF > "$BINDIR/confctl"
32
+ #!${pkgs.ruby}/bin/ruby
33
+ ENV['BUNDLE_GEMFILE'] = "$CONFCTL/Gemfile"
34
+
35
+ require 'bundler'
36
+ Bundler.setup
37
+
38
+ load File.join('$CONFCTL', 'bin/confctl')
39
+ EOF
40
+ chmod +x "$BINDIR/confctl"
41
+ '';
42
+ }