185 Commits

Author SHA1 Message Date
Shelvacu
c1543d606c stuff 2024-12-03 20:11:52 -08:00
Shelvacu
552a603d90 git (finally) 2024-11-25 11:17:21 -08:00
Shelvacu
89be91c6ec stuff 2024-11-25 11:01:30 -08:00
Shelvacu
8c295dbf4a Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-11-25 10:56:15 -08:00
Shelvacu
f13607422d stuff 2024-11-25 10:55:58 -08:00
shelvacu
68ff0b87ca Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-11-25 10:52:02 -08:00
Shelvacu
5ab1b76d48 git configs 2024-11-25 10:43:24 -08:00
Shelvacu
ad25aa6a0f git configs 2024-11-25 10:43:01 -08:00
Shelvacu
9cc7291ea1 Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-11-25 10:42:12 -08:00
Shelvacu
59397af7d3 git configs 2024-11-25 10:42:01 -08:00
shelvacu
d68618bc31 stuff 2024-11-24 12:12:38 -08:00
shelvacu
d7aba29e59 stuff 2024-11-24 12:06:13 -08:00
Shelvacu
456a4878ce nix is dead. long live lix 2024-11-24 11:09:13 -08:00
shelvacu
2b010893cd nix flake update 2024-11-24 00:20:50 -08:00
Shelvacu
33dccc1c8f fix tliam script not exit code failing on fail 2024-11-23 15:35:30 -08:00
Shelvacu
7b019ef9f3 add oscar 2024-11-23 15:31:56 -08:00
Shelvacu
e7b2bff68a add cargo 2024-11-22 18:59:45 -08:00
Shelvacu
24a449e06a add ssh aliases for github gitlab and uninsane 2024-11-22 16:46:52 -08:00
Shelvacu
0a81c1e44e add yt-dlp 2024-11-20 20:45:49 -08:00
Shelvacu
a823567263 stuff 2024-11-15 16:14:30 -08:00
Shelvacu
5e72c629e9 add headsettool 2024-11-15 16:12:08 -08:00
Shelvacu
330d19f304 Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-11-15 16:05:04 -08:00
Shelvacu
cce255cfaf add ns command 2024-11-15 16:04:28 -08:00
Shelvacu
0c5cac492e superban asuswebstorage 2024-11-14 23:17:12 -08:00
Shelvacu
1335b2ef50 Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-11-14 17:25:27 -08:00
Shelvacu
6af04f502e unitsunitsunitsunits 2024-11-14 17:25:12 -08:00
Shelvacu
4505509f31 stuff 2024-11-14 15:14:52 -08:00
shelvacu
c221a643cf nix flake update 2024-11-14 11:32:35 -08:00
shelvacu
12303050e3 nix flake update 2024-11-14 11:15:22 -08:00
Shelvacu
4a62fe396b nix flake update 2024-11-14 00:18:15 -08:00
Shelvacu
577c51d592 nixfmt 2024-11-14 00:11:22 -08:00
Shelvacu
6ddb5d1627 stuff 2024-11-14 00:06:11 -08:00
Shelvacu
52cb4636ae stuff 2024-11-13 23:44:13 -08:00
Shelvacu
3d46260ea7 fix awootrip? 2024-11-13 23:15:15 -08:00
Shelvacu
1812ed20d5 fix sourcetree? 2024-11-13 23:15:09 -08:00
Shelvacu
21a15e6116 stuff 2024-11-13 22:19:17 -08:00
Shelvacu
a56ffd9463 stuff 2024-11-13 21:57:36 -08:00
Shelvacu
966de19436 fix vhich 2024-11-13 15:51:08 -08:00
Shelvacu
605bb09688 stuff 2024-11-13 15:02:30 -08:00
Shelvacu
6a72fb45f9 stuff 2024-11-12 15:28:47 -08:00
Shelvacu
af2d73a77c add nr command 2024-11-12 12:16:39 -08:00
Shelvacu
60f55b0b4a add sdf ssh host 2024-11-12 12:00:27 -08:00
Shelvacu
80e57ba1a8 stuff 2024-11-12 12:00:16 -08:00
Shelvacu
6f8c93442b Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-11-04 16:25:58 -08:00
Shelvacu
2c0d7046ed applets 2024-11-04 16:25:49 -08:00
Shelvacu
b58980525f add info@rfidlabel.com to spam list 2024-11-04 11:16:42 -08:00
Shelvacu
e672d78794 add upgrade-plans@asuswebstorage.com to spam list 2024-11-04 11:00:13 -08:00
Shelvacu
e89f6ce2de stuff 2024-11-03 01:49:18 -08:00
Shelvacu
6963d29cae remap capslock 2024-11-02 16:07:31 -07:00
shelvacu
398408e380 stuff 2024-11-01 00:30:19 -07:00
Shelvacu
3b8a9060d8 some docs maybe 2024-10-30 15:00:06 -07:00
Shelvacu
4a0066051f wip dns stuff 2024-10-29 18:42:36 -07:00
shelvacu
243e2e2917 it works 2024-10-27 13:13:08 -07:00
shelvacu
d6f3a89a53 stuff 2024-10-26 23:07:14 -07:00
shelvacu
96be980c95 Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-10-26 23:01:55 -07:00
Shelvacu
5d038447dc stuff 2024-10-26 23:01:21 -07:00
Shelvacu
1916e9512e stuff 2024-10-26 18:39:59 -07:00
Shelvacu
4b2a048ed7 wip 2024-10-26 18:38:25 -07:00
Shelvacu
1400df6df5 stuff 2024-10-25 21:18:35 -07:00
Shelvacu
fcf61aed64 stuff 2024-10-25 19:18:48 -07:00
shelvacu
72f8d2016a utillinux got renamed 2024-10-24 09:18:44 -07:00
Shelvacu
9a44f26952 add gitlab token 2024-10-23 22:45:23 -07:00
Shelvacu
299090e05c it worrrrrks 2024-10-23 22:28:55 -07:00
shelvacu
96e61ef46a fix some keys 2024-10-23 21:41:52 -07:00
Shelvacu
cb3aa29d9a wip-gitea-sops 2024-10-23 21:31:01 -07:00
Shelvacu
aee5440fde nixfmt 2024-10-23 19:12:43 -07:00
Shelvacu
79c4c5ada6 rework sops config and ssh keys config 2024-10-23 19:06:00 -07:00
shelvacu
65cdbd2ce2 stuff 2024-10-23 19:03:54 -07:00
shelvacu
784f418cd0 stuff 2024-10-19 23:35:56 -07:00
shelvacu
94edcb5f9a stuff 2024-10-19 21:21:24 -07:00
Shelvacu
ee36ed3373 stuff 2024-10-19 20:56:30 -07:00
Shelvacu
89b52cf239 disable som stuff 2024-10-19 20:23:45 -07:00
Shelvacu
c3120e5b79 it evaluates 2024-10-19 19:21:59 -07:00
Shelvacu
565bb08be3 wip 2024-10-19 18:18:53 -07:00
Shelvacu
01aa80919e add more filtering 2024-10-18 13:18:49 -07:00
Shelvacu
32878396bf add to dialout for arduino 2024-10-18 13:09:02 -07:00
Shelvacu
d7087fe6d0 arduinooooooo 2024-10-15 19:04:03 -07:00
Shelvacu
d414d72f52 stuff 2024-10-14 15:23:43 -07:00
Shelvacu
9a2285887c stuff 2024-10-14 15:22:29 -07:00
Shelvacu
c484278721 nix fmt 2024-10-13 11:25:12 -07:00
Shelvacu
3b596662c8 stuff 2024-10-13 11:20:39 -07:00
Shelvacu
960e93581a common packages 2024-10-13 11:20:29 -07:00
Shelvacu
aedf149f9d added bandcamp-collection-downloader 2024-10-12 18:40:38 -07:00
shelvacu
7878ae11b5 fix yt-archiver 2024-10-12 18:38:43 -07:00
Shelvacu
c8f322383d wip adding bandcamp-collection-downloader 2024-10-12 16:26:55 -07:00
Shelvacu
76ce28a5c7 update ms* utility commands 2024-10-12 15:41:39 -07:00
shelvacu
b1491643c9 stuff 2024-10-09 01:05:56 -07:00
Shelvacu
35472eeda6 aaa 2024-10-08 23:30:21 -07:00
shelvacu
9fab2f9061 nix flake update 2024-10-04 16:08:03 -07:00
shelvacu
cd66d41ab6 fmt 2024-10-04 16:08:03 -07:00
Shelvacu
5e052d6cc7 add virtualbox to fw; add z3 package 2024-10-04 16:04:58 -07:00
Shelvacu
5d21668904 mmm stuff 2024-09-30 18:07:28 -07:00
Shelvacu
d9ebd32f10 fmt 2024-09-30 17:09:39 -07:00
Shelvacu
d6ef5a81b3 mmm stuff 2024-09-30 15:19:04 -07:00
Shelvacu
490ef4ea1c mmm stuff 2024-09-30 15:17:27 -07:00
Shelvacu
5a8fe39c38 mmm stuff 2024-09-30 14:46:53 -07:00
Shelvacu
4017b53b45 mmm stuff 2024-09-30 14:39:20 -07:00
Shelvacu
8210d58ad2 mmm stuff 2024-09-30 14:17:02 -07:00
Shelvacu
5352b86faa mmm stuff 2024-09-30 14:07:50 -07:00
Shelvacu
1088e31f8e mmm stuff 2024-09-30 14:06:56 -07:00
Shelvacu
5568637178 stuff 2024-09-27 21:09:38 -07:00
Shelvacu
1f3d770761 stuff 2024-09-27 21:06:43 -07:00
Shelvacu
027f105ecd full wine. all the wine. we drunk nao 2024-09-25 15:06:40 -07:00
shelvacu
2bba10703c Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-09-25 14:50:18 -07:00
shelvacu
7b30a4cdbe more broken builds 2024-09-25 14:50:11 -07:00
Shelvacu
fa9581e1cb add wine 2024-09-25 14:49:38 -07:00
Shelvacu
c367662b51 requireFile-less coopdx 2024-09-24 16:07:18 -07:00
Shelvacu
e3b49965b9 add installer-bootstrap crossbuild 2024-09-24 16:04:06 -07:00
Shelvacu
0618d2798c Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-09-22 20:31:35 -07:00
shelvacu
dec12841b1 Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-09-22 20:31:21 -07:00
Shelvacu
b62779a491 add steam 2024-09-21 22:40:16 -07:00
Shelvacu
c47ee6f459 auto optimise nix store on trip 2024-09-21 14:11:41 -07:00
shelvacu
d2dcffb8a4 nixos-apple-silicon requires nixpkgs unstable 2024-09-21 13:47:37 -07:00
shelvacu
2103fca349 flake update 2024-09-20 13:53:19 -07:00
Shelvacu
75b75fa621 fix plasma integration 2024-09-20 13:47:31 -07:00
Shelvacu
b9037cff8a stuff 2024-09-19 22:52:48 -07:00
Shelvacu
19f71e106b rename mike1 to mmm 2024-09-19 21:41:01 -07:00
Shelvacu
e710eeab87 better coopdx 2024-09-19 21:28:06 -07:00
shelvacu
6b0333d143 preliminary mike1 config 2024-09-19 19:43:36 -07:00
Shelvacu
b318a9a3bc stufff 2024-09-18 14:03:09 -07:00
Shelvacu
cc10b99461 add legtop keys 2024-09-18 14:03:09 -07:00
Shelvacu
2ff3cbe417 cleanup 2024-09-18 11:17:15 -07:00
Shelvacu
6c2e19d398 stuff 2024-09-18 10:35:46 -07:00
Shelvacu
eda2b3085d fix coopdx 2024-09-17 20:07:26 -07:00
Shelvacu
608c4899ec audio 2024-09-17 18:56:52 -07:00
Shelvacu
b54e90049b default verify expectedMac only 2024-09-17 17:23:07 -07:00
Shelvacu
046252da60 add legtop 2024-09-17 17:07:47 -07:00
Shelvacu
d587f2ae84 stuff 2024-09-17 15:48:53 -07:00
Shelvacu
9935f280c0 fix alias 2024-09-17 15:48:26 -07:00
shelvacu
5e62f70951 stuff 2024-09-15 15:48:27 -07:00
shelvacu
c99528ad0a fix minimal for nod 2024-09-15 15:37:47 -07:00
shelvacu
063869e616 stuff 2024-09-15 15:09:38 -07:00
Shelvacu
d365fe304a stuff 2024-09-15 15:03:23 -07:00
Shelvacu
0bce429ad0 stuff 2024-09-15 15:01:28 -07:00
Shelvacu
bb1c2bbbb8 stuff 2024-09-15 14:20:40 -07:00
Shelvacu
b17125ebaf stuff 2024-09-15 14:19:10 -07:00
Shelvacu
7ca34cf82c updaaaaaate 2024-09-14 19:50:12 -07:00
Shelvacu
bfda13b128 massively shrink liam closure size 2024-09-14 14:40:20 -07:00
shelvacu
04d47744d7 screw snmp 2024-09-14 12:45:28 -07:00
Shelvacu
64c031ed71 waydroid 2024-09-14 11:39:35 -07:00
shelvacu
53141d7be7 mark broken sm64coopdx build 2024-09-14 11:00:01 -07:00
Shelvacu
4a2ad61a8b fmt 2024-09-14 10:47:22 -07:00
Shelvacu
12827583f2 stuff 2024-09-14 10:45:23 -07:00
Shelvacu
e6b5c98bcd nixos-rebuild --use-remote-sudo no more 2024-09-14 10:35:42 -07:00
shelvacu
014961aef8 stuff 2024-09-14 00:51:55 -07:00
Shelvacu
ccba74fb9c stuff 2024-09-13 21:30:56 -07:00
Shelvacu
6bb5486180 i dont care about """"unfree"""" 2024-09-13 21:29:33 -07:00
Shelvacu
9dc0718386 reorganize shell functions 2024-09-13 20:48:59 -07:00
Shelvacu
27bd4077cf fmt run 2024-09-13 20:24:23 -07:00
Shelvacu
54abbe179a stuff 2024-09-13 20:20:18 -07:00
Shelvacu
76036a25b2 stuff 2024-09-13 20:19:56 -07:00
Shelvacu
8b062011ad nixvim 2024-09-13 20:18:24 -07:00
Shelvacu
cfb2b44b77 stuff 2024-09-13 19:42:33 -07:00
shelvacu
332d43e768 stuff 2024-09-13 18:04:15 -07:00
Shelvacu
1f8bd06367 allWithBuildDeps -> archive, try to avoid builing iso every time 2024-09-13 17:52:32 -07:00
shelvacu
c7921cb8ed reorg fwupd 2024-09-13 16:35:18 -07:00
shelvacu
74180f9a41 Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-09-13 13:43:25 -07:00
Shelvacu
d80f4b3a02 all da tunderbolt 2024-09-13 13:13:42 -07:00
Shelvacu
4c4c4dc675 more thunderbolt 2024-09-12 20:20:21 -07:00
Shelvacu
46dea07a6f add thunderbolt management pkg 2024-09-12 20:12:58 -07:00
Shelvacu
3e1f3b4c97 verify against permaddrs as well 2024-09-12 16:03:21 -07:00
Shelvacu
56fdf9c128 add pixel 9 pro nix-on-droid key 2024-09-12 15:52:48 -07:00
Shelvacu
a459afdad2 verify system, no more oopsies hopefully 2024-09-11 09:32:57 -07:00
Shelvacu
94e08bc6fe wip 2024-09-10 23:46:16 -07:00
Shelvacu
def7296ec7 formatter run 2024-09-10 20:05:01 -07:00
shelvacu
82819646b1 nix flake update + yeet devver 2024-09-09 20:30:09 -07:00
shelvacu
c31446e3cb coopdx: put baserom in the right spot 2024-09-07 17:28:17 -07:00
Shelvacu
b707e6ae8d add sm64coopdx 2024-09-05 15:10:25 -07:00
Shelvacu
420a2d8d02 aaaaaaa 2024-09-04 23:37:53 -07:00
Shelvacu
0c546acefd nixvim initial 2024-09-04 15:59:08 -07:00
Shelvacu
1b13226c50 F O R M A T 2024-09-03 04:29:32 -07:00
Shelvacu
4876654145 fix initial ps1 2024-09-02 22:57:11 -07:00
shelvacu
9ed4e80418 add bootstrap 2024-09-02 22:44:09 -07:00
shelvacu
46ec04a967 update flake inputs 2024-09-02 02:44:28 -07:00
Shelvacu
311fbb0904 Merge branch 'master' of git.uninsane.org:shelvacu/nix-stuff 2024-09-02 02:24:35 -07:00
Shelvacu
6453c4cdf0 give all the machines different color shells. yay! 2024-09-02 01:50:35 -07:00
Shelvacu
1a74b58b44 stuff 2024-09-01 10:30:31 -07:00
Shelvacu
4f256663ae reorg 2024-08-29 19:35:53 -07:00
shelvacu
4c6df8c5e5 unify some inputs 2024-08-29 09:18:43 -07:00
shelvacu
7312aab991 update flake 2024-08-28 23:11:43 -07:00
shelvacu
c56a26ff6d all is now all all 2024-08-28 22:43:46 -07:00
Shelvacu
88af0f1e93 add curl 2024-08-28 17:17:27 -07:00
Shelvacu
1b3aa80fe9 Merge branch 'restricted-inputs' 2024-08-28 17:15:01 -07:00
shelvacu
fccda582ef gimp 2024-08-23 10:49:20 -07:00
Shelvacu
addf748d1f wip 2024-08-21 17:11:38 -07:00
138 changed files with 8538 additions and 2663 deletions

2
.gitignore vendored
View File

@@ -1,2 +1,2 @@
/result
/result*
.nixos-test-history

View File

@@ -1,40 +0,0 @@
shel_keys: &shel_keys
- &a age1y4zp4ddq6xyffd8fgmn2jkl78qfh4m94gcls2cu6vvjnwwznx5uqywjekm
- &b age1g9sh8u6s344569d3cg8h30g9h7thld5pexcwzc4549jc84jvceqqjt9cfh
- &c age1t5s3txyj403rfecdhq5q2z3cnavy6m543gzyhkl2nu5t8fz0zctqtvm2tj
- &d age1dzdf4rgep3ctk3dnrmrqtdgrchaa8nszfc4dp29gqwsst3z6jyrq57vfsj
- &e age197a33mlf5294amjx59hycctu6wm4l3cu3w7n9rv3fs9340ql64rqjzpr7s
- &f age1sqj8z3feqm2dk3gj8mxpfn5dpqnsmus862e8ayd0d4cdresqffdswcf9ru
- &g age1rz75dqzfd6gulwh270ukmt5amcau6j8dpxgzx8fm6u8sjkyx9usq69y4s2
- &h age148huz6rc3q9xx5t873ncx75sja2sazlescwspxl7lsmxsqkz0apsy8cldp
- &i age1ck6lhd8thjcrdcnkn2epc8npztg0sfswahunjkwcf57rr0xaevys8fh0x6
- &j age13j6l33g0ghk4vezn0qwfal2qmcgqwkv89ejwezpe3n47mw8yxyuslj6y7d
- &k age13x0f3glnz4jvqty2v92cxrrnjcna6ed4qegrhulw9jjy08zuy3aqzvrfc6
machine_host_keys:
- &trip age10lv32k2guszr5y69sez3z5xj92wzmdxvfejd6hm8xr0pmclw2cvq0hk6pe
- &compute-deck-host age1hcqem868xhjdj3lzsvgf0duylwrdp9nqs06a9d0043cpsuhms4as7cqnv4
- &liam age1hkve3khk7fthyrwxjqdf4r37lrqpmnkz6mke7psuphvu2ykynqaq9g6ja5
the_test_key: &test_key age1eqv5759uknu7d46rqyyzsmgt43qumsge33yp2xygapprnt8zu3sqx6kt8w
creation_rules:
- path_regex: secrets/[^/]+$
key_groups:
- age: *shel_keys
- path_regex: ^secrets/liam/
key_groups:
- age:
- *a
- *b
- *c
- *d
- *e
- *f
- *g
- *h
- *i
- *j
- *k
- *liam
- path_regex: ^tests/test_secrets/
key_groups:
- age:
- *test_key

View File

@@ -1,13 +1,31 @@
more just notes for now
---
deploy:
```sh
nixos-rebuild switch --flake .#triple-dezert --target-host trip.shelvacu.com --use-remote-sudo
```
---
build flake on remote machine, including eval:
```sh
git add . && ssh trip nix flake check $(nix flake archive --to ssh://trip --json | jq .path -r)
```
```
---
search for string in closure
```sh
rg search_str $(nix path-info --recursive ./result)
```
or
```sh
rg search_str $(nix path-info --recursive .#qb.trip)
```

View File

@@ -0,0 +1,31 @@
{
config,
lib,
utils,
vacuModuleType,
...
}:
let
for-systemd-services = lib.concatMapAttrs (cert: units: {
"acme-selfsigned-${cert}" = {
wantedBy = units;
before = units;
};
}) config.vacu.acmeCertDependencies;
for-security-acme-certs = lib.concatMapAttrs (cert: units: {
${cert}.reloadServices = units;
}) config.vacu.acmeCertDependencies;
in
lib.optionalAttrs (vacuModuleType == "nixos") {
options.vacu.acmeCertDependencies = lib.mkOption {
default = { };
example = ''
vacu.acmeCertDependencies."mail.example.com" = [ "postfix.service" ];
'';
type = lib.types.attrsOf (lib.types.listOf utils.systemdUtils.lib.unitNameType);
};
config = {
systemd.services = for-systemd-services;
security.acme.certs = for-security-acme-certs;
};
}

48
common/assertions.nix Normal file
View File

@@ -0,0 +1,48 @@
{
lib,
vacuModuleType,
config,
...
}:
let
inherit (lib) mkOption types filter;
fatalAssertions = map (x: x.message) (filter (x: !x.assertion && x.fatal) config.vacu.assertions);
triggeredWarnings = map (x: x.message) (
filter (x: !x.assertion && !x.fatal) config.vacu.assertions
);
withAsserts =
x:
if fatalAssertions != [ ] then
throw "\nFailed assertions:\n${lib.concatStringsSep "\n" (map (x: "- ${x}") fatalAssertions)}"
else
lib.showWarnings triggeredWarnings x;
adapter = {
config = {
assertions = map (x: { inherit (x) assertion message; }) (
filter (x: x.fatal) config.vacu.assertions
);
warnings = map (x: x.message) (filter (x: !x.assertion && !x.fatal) config.vacu.assertions);
};
};
in
{
options.vacu.assertions = mkOption {
default = [ ];
type = types.listOf (
types.submodule {
options.assertion = mkOption { type = types.bool; };
options.message = mkOption { type = types.str; };
options.fatal = mkOption {
type = types.bool;
default = true;
};
}
);
};
options.vacu.withAsserts = mkOption {
readOnly = true;
default = withAsserts;
};
}
// (if vacuModuleType != "plain" then adapter else { })

View File

@@ -1,86 +0,0 @@
{ config, lib, pkgs, ... }: let
inherit (lib) mkOption types;
cfg = builtins.attrValues config.vacu.shell.functions;
enabled = builtins.filter (o: o.enable) cfg;
writeShellFunction = name: text: pkgs.writeTextFile {
inherit name;
executable = false;
destination = "/share/vacufuncs/${name}";
text = ''
${text}
'';
checkPhase = ''
${pkgs.stdenv.shellDryRun} "$target"
'';
};
in {
options = {
vacu.shell.functionsDir = mkOption {
type = types.path;
};
vacu.shell.interactiveLines = mkOption {
type = types.lines;
default = "";
};
vacu.shell.functions = mkOption {
default = {};
type = types.attrsOf (types.submodule ({ name, config, options, ... }: {
options = {
name = mkOption {
type = types.str;
default = name;
readonly = true;
};
content = mkOption {
type = types.str;
default = "";
};
enable = mkOption {
type = types.bool;
default = config.content != "";
defaultText = ''${name}.content != ""'';
};
};
}));
};
};
config = {
_module.args.vaculib.writeShellFunction = writeShellFunction;
vacu.shell.interactiveLines = ''
if [[ $- == *i* ]] && [[ -f ${config.vacu.shell.functionsDir}/vacureload ]]; then
function __vacushell_load() { eval "$(cat ${config.vacu.shell.functionsDir}/vacureload)"; }
__vacushell_load
unset __vacushell_load
fi
'';
vacu.packages.vacureload.enable = true;
vacu.packages.vacureload.package = let
inherit (config.vacu.shell) functionsDir;
in writeShellFunction "vacureload" ''
declare -gA vacuShellFunctionsLoaded
if ! [[ -f ${functionsDir}/vacureload ]]; then
echo "vacureload: I think that's my cue to leave (${functionsDir}/vacureload not found, assuming vacureload-less config has been loaded and unloading myself)" 1>&2
for funcname in "''${!vacuShellFunctionsLoaded[@]}"; do
unset -f $funcname
done
return
fi
for funcname in "''${!vacuShellFunctionsLoaded[@]}"; do
if ! [[ -f ${functionsDir}/$funcname ]]; then
unset -f $funcname
fi
done
for fullPath in ${functionsDir}/*; do
local funcname="$(basename "$fullPath")"
local followedPath="$(readlink -f "$fullPath")"
if [[ "''${vacuShellFunctionsLoaded[$funcname]}" != "$followedPath" ]]; then
unset -f $funcname
eval "function ''${funcname}() { if [[ -f '$fullPath' ]]; then eval "'"$'"(cat '$fullPath')"'"'"; else echo '$funcname is no longer there, kindly removing myself.' 1>&2; unset $funcname; return 1; fi }"
vacuShellFunctionsLoaded[$funcname]=$followedPath
fi
unset followedPath
unset funcname
done
'';
};
}

View File

@@ -1,7 +1,12 @@
# todo: rename this module
# stuff that does actual configuring (so can't be in ./module.nix) but works in nixos module, home-manager modules, and nix-on-droid modules
{ inputs, ... }:
{
inputs,
vacuModuleType,
lib,
...
}:
lib.optionalAttrs (vacuModuleType != "plain") {
nix.registry.vacu.to = {
type = "path";
path = inputs.self.outPath;

321
common/default.nix Normal file
View File

@@ -0,0 +1,321 @@
{
config,
pkgs,
lib,
inputs,
vacuModuleType,
...
}:
let
inherit (lib) mkOption types;
inherit (inputs) self;
expectedModuleTypes = [
"nixos"
"nix-on-droid"
"plain"
];
in
if !builtins.elem vacuModuleType expectedModuleTypes then
builtins.throw "error: unrecognized vacuModuleType ${builtins.toString vacuModuleType}"
else
{
imports = [
./package-set.nix
./shell
./nixvim.nix
./ssh.nix
./nix.nix
./verify-system
./defaultPackages.nix
./lib
./sops.nix
./dns
./assertions.nix
./common-but-not.nix
./nixos.nix
./nix-on-droid.nix
./nixos-rebuild.nix
./minimal-nixos.nix
./acmeDependencies.nix
./nix-on-droid.nix
./remapCapsLock.nix
./sourceTree.nix
./units-impl.nix
./units-config.nix
./lix.nix
./git.nix
./repos-options.nix
./repos-impl.nix
];
options = {
vacu.rootCAs = mkOption { type = types.listOf types.str; };
vacu.versionId = mkOption {
type = types.str;
readOnly = true;
};
vacu.versionInfo = mkOption { readOnly = true; };
vacu.hostName = mkOption {
type = types.nullOr types.str;
default = null;
};
vacu.shortHostName = mkOption {
type = types.nullOr types.str;
default = config.vacu.hostName;
};
vacu.nixvimPkg = mkOption { readOnly = true; };
vacu.systemKind = mkOption {
type = types.enum [
"minimal"
"desktop" # need a better name for this; should include laptops; everything I intend to get computery-stuff done on.
"container"
"server"
];
};
vacu.vnopnCA = mkOption {
readOnly = true;
type = types.str;
};
};
config = {
# vacu.systemKind = lib.mkIf (vacuModuleType == "plain") ("server"); #TODO: should be mkDefault, removed for debugging
vacu.versionId = toString (self.shortRev or self.dirtyShortRev);
vacu.versionInfo = {
id = self.rev or self.dirtyRev;
flakePath = self.outPath;
inherit inputs;
inherit vacuModuleType;
} // (if config.nixpkgs ? flake then { nixpkgs = config.nixpkgs.flake.source; } else { });
vacu.nix.caches.nixcache-shelvacu = {
url = "https://nixcache.shelvacu.com/";
keys = [ "nixcache.shelvacu.com:73u5ZGBpPRoVZfgNJQKYYBt9K9Io/jPwgUfuOLsJbsM=" ];
};
vacu.nix.caches.nix-community = {
url = "https://nix-community.cachix.org/";
keys = [ "nix-community.cachix.org-1:mB9FSh9qf2dCimDSUo8Zy7bkq5CX+/rkCWyvRCYg3Fs=" ];
};
vacu.nix.caches.nix-on-droid = {
url = "https://nix-on-droid.cachix.org/";
keys = [ "nix-on-droid.cachix.org-1:56snoMJTXmDRC1Ei24CmKoUqvHJ9XCp+nidK7qkMQrU=" ];
};
vacu.nix.caches.nixos = {
url = "https://cache.nixos.org/";
keys = [ "cache.nixos.org-1:6NCHdD59X431o0gWypbMrAURkbJ16ZPMQFGspcDShjY=" ];
};
vacu.git.enable = config.vacu.systemKind == "server" || config.vacu.systemKind == "desktop";
vacu.git.config = {
init.defaultBranch = "master";
pull.rebase = false;
user.name = "Shelvacu";
user.email = "git@shelvacu.com";
author.name = "Shelvacu";
author.email = "git@shelvacu.com";
committer.name = "Shelvacu on ${config.vacu.hostName}";
committer.email = "git@shelvacu.com";
user.useConfigOnly = true;
checkout.workers = 0;
# We *could* use atomic writes, but those are slow! Are you sure????? - git, still living in the 90s
# Yes git, I'm sure
core.fsync = "all";
diff.mnemonicPrefix = true;
gc.reflogExpire = "never";
gc.reflogExpireUnreachable = "never";
url."https://github.com/".insteadOf = [ "hgh:" "github-http:" "github-https:" ];
url."git@github.com:".insteadOf = [ "sgh:" "gh:" "github-ssh:" ];
url."git@github.com:shelvacu/".insteadOf = [ "vgh:" ];
url."https://gitlab.com/".insteadOf = [ "hgl:" "gitlab-http:" "gitlab-https:" ];
url."git@gitlab.com:".insteadOf = [ "sgl:" "gl:" "gitlab-ssh:" ];
url."git@gitlab.com:shelvacu/".insteadOf = [ "vgl:" ];
url."https://git.uninsane.org/".insteadOf = [ "hu:" "uninsane-http:" "uninsane-https:" ];
url."git@git.uninsane.org:".insteadOf = [ "u:" "su:" "uninsane-ssh" ];
url."git@git.uninsane.org:shelvacu/".insteadOf = [ "vu:" ];
};
vacu.vnopnCA = ''
-----BEGIN CERTIFICATE-----
MIIBnjCCAUWgAwIBAgIBBTAKBggqhkjOPQQDAjAgMQswCQYDVQQGEwJVUzERMA8G
A1UEAxMIdm5vcG4gQ0EwHhcNMjQwODEyMjExNTQwWhcNMzQwODEwMjExNTQwWjAg
MQswCQYDVQQGEwJVUzERMA8GA1UEAxMIdm5vcG4gQ0EwWTATBgcqhkjOPQIBBggq
hkjOPQMBBwNCAARqRbSeq00FfYUGeCHVkzwrjrydI56T12xy+iut0c4PemSuhyxC
AgfdKYtDqMNZmSqMaLihzkBenD0bN5i0ndjho3AwbjAPBgNVHRMBAf8EBTADAQH/
MCwGA1UdHgEB/wQiMCCgGDAKhwgKTkwA///8ADAKgggudDJkLmxhbqEEMAKBADAO
BgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYEFAjSkbJQCQc1WP6nIP5iLDIKGFrdMAoG
CCqGSM49BAMCA0cAMEQCIFtyawkZqFhvzgmqG/mYNNO6DdsQTPQ46x/08yrEiiF4
AiA+FwAPqX+CBkaSdIhuhv1kIecmvacnDL5kpyB+9nDodw==
-----END CERTIFICATE-----
'';
vacu.rootCAs = [ config.vacu.vnopnCA ];
vacu.ssh.authorizedKeys = {
# pixel6pro-termux = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIC4LYvUe9dsQb9OaTDFI4QKPtMmOHOGLwWsXsEmcJW86";
# t460s = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIHcYwYy9/0Gu/GsqS72Nkz6OkId+zevqXA/aTIcvqflp";
# pixel6pro-nod = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFsErA6M9LSHj2hPlLuHD8Lpei7WjMup1JxI1vxA6B8W";
compute-deck = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIKoy1TrmfhBGWtVedgOM1FB1oD2UdodN3LkBnnLx6Tug";
triple-dezert = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAICVeSzDkGTueZijB0xUa08e06ovAEwwZK/D+Cc7bo91g";
triple-dezert-root = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOtwtao/TXbiuQOYJbousRPVesVcb/2nP0PCFUec0Nv8";
compute-deck-root = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIAxAFFxQMXAgi+0cmGaNE/eAkVfEl91wafUqFIuAkI5I";
pro1x-nod = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIDcRDekd8ZOYfQS5X95/yNof3wFYIbHqWeq4jY0+ywQX";
fw-root = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIGHLPOxRd68+DJ/bYmqn0wsgwwIcMSMyuU1Ya16hCb/m";
fw = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAINQ2c0GzlVMjV06CS7bWbCaAbzG2+7g5FCg/vClJPe0C";
pixel9pro-nod = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAINznGot+L8kYoVQqdLV/R17XCd1ILMoDCILOg+I3s5wC";
legtop = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOre0FnYDm3arsFj9c/l5H2Q8mdmv7kmvq683pL4heru";
};
vacu.ssh.config = ''
Host deckvacu
User deck
Host rsb
User user
HostName finaltask.xyz
Port 2222
Host awoo
HostName 45.142.157.71
Host trip
HostName trip.shelvacu.com
Port 6922
Host liam
HostName 178.128.79.152
Host pluto
HostName pluto.somevideogam.es
Host sdf
HostName tty.sdf.org
Host u
User git
HostName git.uninsane.org
Host gl
User git
HostName gitlab.com
Host gh
User git
HostName github.com
Host *
User shelvacu
GlobalKnownHostsFile ${pkgs.writeText "known_hosts" config.vacu.ssh.knownHostsText}
'';
vacu.ssh.knownHosts = {
#public hosts
"github.com".publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOMqqnkVzrm0SdG6UOoqKLsabgH5C9okWi0dh2l9GKJl";
"gitlab.com".publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIAfuCHKVTjquxvt6CM6tdG4SLp1Btn/nOeHHE5UOzRdf";
"git.sr.ht".publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIMZvRd4EtM7R+IHVMWmDkVU3VLQTSwQDSAvW0t2Tkj60";
"sdf.org" = {
extraHostNames = [ "tty.sdf.org" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIJJk3a190w/1TZkzVKORvz/kwyKmFY144lVeDFm80p17";
};
#colin's stuff
"uninsane.org" = {
extraHostNames = [ "git.uninsane.org" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOfdSmFkrVT6DhpgvFeQKm3Fh9VKZ9DbLYOPOJWYQ0E8";
};
"desko" = {
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFw9NoRaYrM6LbDd3aFBc4yyBlxGQn8HjeHd/dZ3CfHk";
};
#daymocker's stuff
"pluto" = {
extraHostNames = [ "74.208.184.137" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAICpHY4fLZ1hNuB2oRQM7R3b4eQyIHbFB45ZYp3XCELLg";
};
#powerhouse hosts
"ostiary" = {
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIBSYyd1DGPXGaV4mD34tUbXvbtIi/Uv2otoMUsCkxRse";
};
"habitat" = {
# previously known as zigbee-hub
extraHostNames = [ "10.78.79.114" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIBJxwUYddOxgViJDOiokfaQ6CsCx/Sw+b3IisdJv8zFN";
};
"vnopn" = {
extraHostNames = [
"10.78.79.1"
"vnopn.t2d.lan"
];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIEMgJE8shlTYF3nxKR/aILd1SzwDwhtCrjz9yHL7lgSZ";
};
#work laptop
"tebbs-MBP" = {
extraHostNames = [ "10.244.10.3" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIKO/ks07zSByDH/qmDrghtBSFwWnze2s62zEmtXwaMJe";
};
#personal hosts
trip = {
extraHostNames = [
"triple-dezert"
"trip.shelvacu.com"
"[trip.shelvacu.com]:6922"
];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIGUQux9V0mSF5IauoO1z311NXR7ymEbwRMzT+OaaNQr+";
};
servacu = {
extraHostNames = [
"mail.dis8.net"
"servacu.shelvacu.com"
];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIE+E6na7np0HnBV2X7owno+Fg+bNNRSHLxO6n1JzdUTV";
};
finaltask = {
extraHostNames = [
"rsb"
"finaltask.xyz"
"[finaltask.xyz]:2222"
];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIPTx8WBNNKBVRV98HgDChpd59SHbreJ87SXU+zOKan6y";
};
compute-deck = {
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIGt43GmXCxkl5QjgPQ/QimW11lKfXmV4GFWvlxQSf4TQ";
};
"2esrever" = {
extraHostNames = [
"10.4.5.218"
"10.244.46.71"
];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIH0LnPrJxAdffZ//uRe3NBiIfFCBNMLqKVylkyU0llvT";
};
awoo = {
extraHostNames = [ "45.142.157.71" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOQaDjjfSK8jnk9aFIiYH9LZO4nLY/oeAc7BKIPUXMh1";
};
deckvacu = {
publicKey = "ecdsa-sha2-nistp256 AAAAE2VjZHNhLXNoYTItbmlzdHAyNTYAAAAIbmlzdHAyNTYAAABBBEa8qpFkIlLLJkH8rmEAn6/MZ9ilCGmEQWC3CeFae7r1kOqfwRk0nq0oyOGJ50uIh+PpwEh3rbgq6mLfpRfsFmM=";
};
liam = {
extraHostNames = [
"liam.dis8.net"
"178.128.79.152"
];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIHOqJYVHOIFmEA5uRbbirIupWvyBLAFwic/8EZQRdN/c";
};
fw = {
extraHostNames = [ "fw.t2d.lan" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIA6lX25mCy35tf1NpcHMAdeRgvT7l0Dw0FWBH3eX4TE2";
};
legtop = {
extraHostNames = [
"lt"
"legtop.t2d.lan"
];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIKvunOGsmHg8igMGo0FpoXaegYI20wZylG8nsMFY4+JL";
};
mmm = {
extraHostNames = [
"mmm.t2d.lan"
"10.78.79.11"
];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFsorkZ3rIZ2lLigwQWfA64xZRlt5lk6QPzypg55eLlD";
};
};
};
}

View File

@@ -0,0 +1,85 @@
{
pkgs,
config,
inputs,
lib,
...
}:
lib.mkMerge [
(lib.mkIf (config.vacu.systemKind != "minimal" && config.vacu.systemKind != "container") {
vacu.packages =
(with pkgs; [
home-manager
nix-index
rclone
termscp
man
neovim
nmap
ruby
(p7zip.override { enableUnfree = true; })
tcpdump
cargo
])
++ [
inputs.nix-search-cli.packages.${pkgs.system}.default
inputs.nix-inspect.packages.${pkgs.system}.default
];
})
{
vacu.packages = (with pkgs; [
nixos-rebuild
which
nano
vim
wget
screen
tmux
lsof
htop
mosh
dnsutils
iperf3
rsync
ethtool
sshfs
ddrescue
pciutils
ncdu
pv
unzip
file
ripgrep
jq
tree
iputils
ssh-to-age
sops
inetutils
diffutils
findutils
util-linux
tzdata
hostname
gnugrep
gnused
gnutar
bzip2
gzip
xz
zip
unzip
openssh
dig
bash
usbutils
psutils
killall
git
curl
gnutls
]) ++ [
(config.vacu.units.finalPackage)
];
}
]

15
common/dns/default.nix Normal file
View File

@@ -0,0 +1,15 @@
{
dns,
lib,
...
}:
let
inherit (lib) mkOption types;
in
{
imports = [ ./jean-luc.org.nix ];
options.vacu.dns = mkOption {
default = { };
type = types.attrsOf dns.lib.types.zone;
};
}

View File

@@ -0,0 +1,27 @@
{
dns,
...
}:
let
inherit (dns.lib.combinators) spf mx;
in
{
vacu.dns."jean-luc.org" = {
SOA = {
nameServer = "ns51.cloudns.net";
adminEmail = "test@example.com";
serial = 123456;
};
NS = [
"ns51.cloudns.net"
"ns52.cloudns.net"
"ns53.cloudns.net"
"ns54.cloudns.net"
];
A = [ "1.2.3.4" ];
TXT = [
(spf.strict [ "1.2.3.4" ])
];
subdomains."in".MX = [ (mx.mx 0 "a.b") ];
};
}

77
common/git.nix Normal file
View File

@@ -0,0 +1,77 @@
{
lib,
config,
pkgs,
vacuModuleType,
...
}:
let
inherit (lib) types;
cfg = config.vacu.git;
in
{ imports = [
{
# https://github.com/NixOS/nixpkgs/blob/e8c38b73aeb218e27163376a2d617e61a2ad9b59/nixos/modules/programs/git.nix#L16
options.vacu.git = {
package = lib.mkPackageOption pkgs "git" {};
enable = lib.mkEnableOption "git";
config = lib.mkOption {
type =
let
gitini = types.attrsOf (types.attrsOf types.anything);
in
types.either gitini (types.listOf gitini) // {
merge = loc: defs:
let
config = builtins.foldl'
(acc: { value, ... }@x: acc // (if builtins.isList value then {
ordered = acc.ordered ++ value;
} else {
unordered = acc.unordered ++ [ x ];
}))
{
ordered = [ ];
unordered = [ ];
}
defs;
in
[ (gitini.merge loc config.unordered) ] ++ config.ordered;
};
default = [];
};
lfs.enable = lib.mkEnableOption "git lfs";
lfs.package = lib.mkPackageOption pkgs "git-lfs" {};
configText = lib.mkOption {
readOnly = true;
type = types.str;
};
};
config.vacu.git.configText = lib.concatMapStringsSep "\n" lib.generators.toGitINI cfg.config;
}
(lib.mkIf cfg.enable { vacu.packages.git = { enable = true; package = cfg.package; }; })
(lib.mkIf (cfg.enable && cfg.lfs.enable) {
vacu.packages.git-lfs = { enable = true; package = cfg.lfs.package; };
vacu.git.config = let bin = lib.getExe cfg.lfs.package; in {
filter.lfs = {
clean = "${bin} clean -- %f";
smudge = "${bin} smudge -- %f";
process = "${bin} filter-process";
required = true;
};
};
})
(lib.optionalAttrs (vacuModuleType == "nixos") {
vacu.assertions = [
{
assertion = !(cfg.enable && config.programs.git.enable);
message = "vacu.git and programs.git should not both be enabled";
}
];
})
(lib.optionalAttrs (vacuModuleType == "nixos" || vacuModuleType == "nix-on-droid") {
environment = lib.mkIf (cfg.enable && cfg.config != []) {
etc.gitconfig.text = cfg.configText;
};
})
]; }

View File

@@ -1,5 +1,7 @@
{ ... }: let
{ ... }:
let
in {
in
{
imports = [ ./common-but-not.nix ];
}

40
common/lib/default.nix Normal file
View File

@@ -0,0 +1,40 @@
{ lib, config, ... }:
let
inherit (builtins) isList;
mkOutOption =
val:
lib.mkOption {
readOnly = true;
default = val;
}
;
listToIndexAttrs = list:
let
thing = lib.foldl (acc: val:
{
index = acc.index + 1;
result = acc.result // { ${toString acc.index} = val; };
}
) { result = {}; index = 0; } list;
in
assert isList list;
thing.result
;
in
{
imports = [
./makeWrapper.nix
./duplicates.nix
];
options.vacu.vaculib = lib.mkOption {
type = lib.types.anything;
};
config._module.args.vaculib = config.vacu.vaculib;
config.vacu.vaculib = {
inherit mkOutOption;
inherit listToIndexAttrs;
};
}

85
common/lib/duplicates.nix Normal file
View File

@@ -0,0 +1,85 @@
{
lib,
config,
vaculib,
...
}:
let
inherit (builtins) isString isList isFunction isAttrs;
pathFromStr = str:
assert isString str;
if str == "" then [] else
lib.splitString "." str
;
/**
For each value, make a list of each attr name that has that value.
Values must be `toString`able, and are deduped based on the output of `toString`.
# Type
```
findDuplicates :: { a :: b } -> { String :: [ a ] }
```
# Examples
:::{.example}
## `vaculib.findDuplicates` usage example
```nix
findDuplicates { a = 1; b = 2; c = 3; x = 1; y = 2; }
=> { "1" = [ "a" "x" ]; "2" = [ "b" "y" ]; }
```
:::
*/
findDuplicates = attrs:
let
occurances = lib.foldl (acc: name: value:
let
key = toString value;
in
acc // { ${key} = (acc.${key} or []) ++ [ name ]; }
) {} attrs;
in
assert isAttrs attrs;
lib.filterAttrs (_: names: (builtins.length names) > 1) occurances
;
# returns a list of attrSets suitable for vacu.assertions
assertNoDuplicatesModule = among: attr:
let
list_or_attrs = lib.getAttrFromPath (pathFromStr among) config;
attrs =
if isAttrs list_or_attrs
then list_or_attrs
else vaculib.listToIndexAttrs list_or_attrs
;
innerPath = pathFromStr attr;
valueMap = (v: lib.getAttrFromPath innerPath v);
duplicates = findDuplicates (lib.mapAttrs (_: valueMap) attrs);
valueName = if attr == "" then "value" else "`${attr}`";
messages = lib.mapAttrsToList (duplicate: names:
let
pretty = name: "`${name}`";
prettyNames = map pretty names;
in
"Duplicate found in ${among}: ${lib.concatStringsSep ", " prettyNames} all have the same ${valueName}: ${duplicate}"
) duplicates;
in
assert isString among;
assert isString attr;
assert (isList list_or_attrs) || (isAttrs list_or_attrs);
{
config.vacu.assertions = map (message: {
assertion = false;
inherit message;
}) messages;
}
;
in
{
config.vacu.vaculib = {
inherit findDuplicates;
inherit assertNoDuplicatesModule;
};
}

View File

@@ -0,0 +1,97 @@
{
pkgs,
lib,
...
}:
let
inherit (lib)
optionals
optional
mapAttrsToList
concatMap
escapeShellArg
escapeShellArgs
;
in
{
config.vacu.vaculib.makeWrapper =
{
original,
new,
argv0 ? null,
inherit_argv0 ? false,
resolve_argv0 ? false,
set ? { },
set_default ? { },
unset ? [ ],
chdir ? null,
run ? [ ],
prepend_flags ? [ ],
add_flags ? [ ],
append_flags ? [ ],
runtimeHook ? null,
}@args:
let
prependFlags = prepend_flags ++ add_flags;
escapeFlags = escapeShellArgs;
# escapeFlags = flags: builtins.concatStringsSep " " (map escapeShellArg flags);
originalBin = if lib.isDerivation original then lib.getExe original else original;
makeWrapperFlags =
(optionals (argv0 != null) [
"--argv0"
argv0
])
++ (optional inherit_argv0 "--inherit-argv0")
++ (optional resolve_argv0 "--resolve-argv0")
++ (mapAttrsToList (k: v: [
"--set"
k
v
]) set)
++ (mapAttrsToList (k: v: [
"--set-default"
k
v
]) set_default)
++ (concatMap (k: [
"--unset"
k
]) unset)
++ (optionals (chdir != null) [
"--chdir"
chdir
])
++ (concatMap (k: [
"--run"
k
]) run)
++ (optionals (prependFlags != [ ]) [
"--add-flags"
(escapeFlags prependFlags)
])
++ (optionals (append_flags != [ ]) [
"--append-flags"
(escapeFlags append_flags)
]);
in
pkgs.stdenvNoCC.mkDerivation {
name = new;
nativeBuildInputs = [ pkgs.makeWrapper ];
phases = [ "installPhase" ];
installPhase = ''
runHook preInstall
mkdir -p $out/bin
makeWrapper ${escapeShellArg originalBin} $out/bin/${escapeShellArg new} ${escapeShellArgs makeWrapperFlags}
runHook postInstall
'';
inherit runtimeHook;
meta.mainProgram = new;
};
}

7
common/lix.nix Normal file
View File

@@ -0,0 +1,7 @@
{
inputs,
vacuModuleType,
...
}: if vacuModuleType == "nixos" then {
imports = [ inputs.lix-module.nixosModules.default ];
} else {}

47
common/minimal-nixos.nix Normal file
View File

@@ -0,0 +1,47 @@
{
config,
pkgs,
lib,
vacuModuleType,
...
}:
let
inherit (lib) mkIf mkDefault;
in
lib.optionalAttrs (vacuModuleType == "nixos") {
config = mkIf (config.vacu.systemKind == "minimal") {
programs.git.lfs.enable = false;
programs.git.package = pkgs.gitMinimal;
# mostly copied from nixos's /profiles/minimal.nix
environment.noXlibs = mkDefault true;
documentation.enable = mkDefault false;
documentation.doc.enable = mkDefault false;
documentation.info.enable = mkDefault false;
documentation.man.enable = mkDefault false;
documentation.nixos.enable = mkDefault false;
# Perl is a default package.
environment.defaultPackages = mkDefault [ ];
environment.stub-ld.enable = false;
# The lessopen package pulls in Perl.
programs.less.lessopen = mkDefault null;
programs.command-not-found.enable = mkDefault false;
services.logrotate.enable = mkDefault false;
services.udisks2.enable = mkDefault false;
xdg.autostart.enable = mkDefault false;
xdg.icons.enable = mkDefault false;
xdg.mime.enable = mkDefault false;
xdg.sounds.enable = mkDefault false;
};
}

View File

@@ -1,228 +0,0 @@
{ config, pkgs, lib, inputs, ... }: let
inherit (lib) mkOption types;
inherit (inputs) self;
in {
imports = [ ./package-set.nix ./not-aliases.nix ./ssh.nix ];
options = {
vacu.nix.extraSubstituters = mkOption { type = types.listOf types.str; };
vacu.nix.extraTrustedKeys = mkOption { type = types.listOf types.str; };
vacu.rootCAs = mkOption { type = types.listOf types.str; };
vacu.versionId = mkOption { type = types.str; readOnly = true; };
vacu.versionInfo = mkOption { readOnly = true; };
};
config = {
vacu.packages = with pkgs; [
home-manager
nixos-rebuild
which
nano
vim
wget
screen
tmux
lsof
htop
mosh
dnsutils
iperf3
nmap
rsync
ethtool
sshfs
ddrescue
pciutils
ncdu
nix-index
git
pv
unzip
file
ripgrep
jq
units
tree
rclone
iputils
ssh-to-age
sops
inetutils
neovim
diffutils
findutils
utillinux
tzdata
hostname
man
gnugrep
gnused
gnutar
bzip2
gzip
xz
zip
unzip
openssh
dig
bash
termscp
usbutils
ruby
psutils
killall
git
inputs.nix-search-cli.packages.${pkgs.system}.default
inputs.nix-inspect.packages.${pkgs.system}.default
];
vacu.versionId = toString (self.shortRev or self.dirtyShortRev);
vacu.versionInfo = {
id = config.vacu.versionId;
flakePath = self.outPath;
};
vacu.nix.extraSubstituters = [
"https://nixcache.shelvacu.com/"
"https://nix-community.cachix.org/"
"https://nix-on-droid.cachix.org/"
];
vacu.nix.extraTrustedKeys = [
"nix-community.cachix.org-1:mB9FSh9qf2dCimDSUo8Zy7bkq5CX+/rkCWyvRCYg3Fs="
"nixcache.shelvacu.com:73u5ZGBpPRoVZfgNJQKYYBt9K9Io/jPwgUfuOLsJbsM="
"nix-on-droid.cachix.org-1:56snoMJTXmDRC1Ei24CmKoUqvHJ9XCp+nidK7qkMQrU="
];
vacu.rootCAs = [
''
-----BEGIN CERTIFICATE-----
MIIBnjCCAUWgAwIBAgIBBTAKBggqhkjOPQQDAjAgMQswCQYDVQQGEwJVUzERMA8G
A1UEAxMIdm5vcG4gQ0EwHhcNMjQwODEyMjExNTQwWhcNMzQwODEwMjExNTQwWjAg
MQswCQYDVQQGEwJVUzERMA8GA1UEAxMIdm5vcG4gQ0EwWTATBgcqhkjOPQIBBggq
hkjOPQMBBwNCAARqRbSeq00FfYUGeCHVkzwrjrydI56T12xy+iut0c4PemSuhyxC
AgfdKYtDqMNZmSqMaLihzkBenD0bN5i0ndjho3AwbjAPBgNVHRMBAf8EBTADAQH/
MCwGA1UdHgEB/wQiMCCgGDAKhwgKTkwA///8ADAKgggudDJkLmxhbqEEMAKBADAO
BgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYEFAjSkbJQCQc1WP6nIP5iLDIKGFrdMAoG
CCqGSM49BAMCA0cAMEQCIFtyawkZqFhvzgmqG/mYNNO6DdsQTPQ46x/08yrEiiF4
AiA+FwAPqX+CBkaSdIhuhv1kIecmvacnDL5kpyB+9nDodw==
-----END CERTIFICATE-----
''
];
vacu.ssh.authorizedKeys = [
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIC4LYvUe9dsQb9OaTDFI4QKPtMmOHOGLwWsXsEmcJW86" # Termux on pixel6pro
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIHcYwYy9/0Gu/GsqS72Nkz6OkId+zevqXA/aTIcvqflp" # t460s windows
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFsErA6M9LSHj2hPlLuHD8Lpei7WjMup1JxI1vxA6B8W" # pixel6pro nix-on-droid
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIKoy1TrmfhBGWtVedgOM1FB1oD2UdodN3LkBnnLx6Tug" # compute-deck
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAICVeSzDkGTueZijB0xUa08e06ovAEwwZK/D+Cc7bo91g" # triple-dezert
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOtwtao/TXbiuQOYJbousRPVesVcb/2nP0PCFUec0Nv8" # triple-dezert (root)
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIAxAFFxQMXAgi+0cmGaNE/eAkVfEl91wafUqFIuAkI5I" # compute-deck (root)
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIDcRDekd8ZOYfQS5X95/yNof3wFYIbHqWeq4jY0+ywQX" # pro1x nix-on-droid
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIExSObd1lZprdqAFLqFhtxDEckV0q/vZZIYqrYFKfkoC" # devver
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIGHLPOxRd68+DJ/bYmqn0wsgwwIcMSMyuU1Ya16hCb/m" # fw (root)
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAINQ2c0GzlVMjV06CS7bWbCaAbzG2+7g5FCg/vClJPe0C" # fw
];
vacu.ssh.config = ''
Host deckvacu
User deck
Host rsb
User user
HostName finaltask.xyz
Port 2222
Host awoo
HostName 45.142.157.71
Host trip
HostName trip.shelvacu.com
Port 6922
Host liam
HostName 178.128.79.152
Host pluto
HostName pluto.somevideogam.es
Host *
User shelvacu
GlobalKnownHostsFile ${pkgs.writeText "known_hosts" config.vacu.ssh.knownHostsText}
'';
vacu.ssh.knownHosts = {
#public hosts
"github.com".publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOMqqnkVzrm0SdG6UOoqKLsabgH5C9okWi0dh2l9GKJl";
"gitlab.com".publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIAfuCHKVTjquxvt6CM6tdG4SLp1Btn/nOeHHE5UOzRdf";
"git.sr.ht".publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIMZvRd4EtM7R+IHVMWmDkVU3VLQTSwQDSAvW0t2Tkj60";
#colin's stuff
"uninsane.org" = {
extraHostNames = [ "git.uninsane.org" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOfdSmFkrVT6DhpgvFeQKm3Fh9VKZ9DbLYOPOJWYQ0E8";
};
"desko" = {
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFw9NoRaYrM6LbDd3aFBc4yyBlxGQn8HjeHd/dZ3CfHk";
};
#daymocker's stuff
"pluto" = {
extraHostNames = [ "74.208.184.137" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAICpHY4fLZ1hNuB2oRQM7R3b4eQyIHbFB45ZYp3XCELLg";
};
#powerhouse hosts
"ostiary" = {
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIBSYyd1DGPXGaV4mD34tUbXvbtIi/Uv2otoMUsCkxRse";
};
"habitat" = { # previously known as zigbee-hub
extraHostNames = [ "10.78.79.114" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIBJxwUYddOxgViJDOiokfaQ6CsCx/Sw+b3IisdJv8zFN";
};
"vnopn" = {
extraHostNames = [ "10.78.79.1" "vnopn.t2d.lan" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIEMgJE8shlTYF3nxKR/aILd1SzwDwhtCrjz9yHL7lgSZ";
};
#work laptop
"tebbs-MBP" = {
extraHostNames = [ "10.244.10.3" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIKO/ks07zSByDH/qmDrghtBSFwWnze2s62zEmtXwaMJe";
};
#personal hosts
trip = {
extraHostNames = [ "triple-dezert" "trip.shelvacu.com" "[trip.shelvacu.com]:6922" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIGUQux9V0mSF5IauoO1z311NXR7ymEbwRMzT+OaaNQr+";
};
servacu = {
extraHostNames = [ "mail.dis8.net" "servacu.shelvacu.com" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIE+E6na7np0HnBV2X7owno+Fg+bNNRSHLxO6n1JzdUTV";
};
finaltask = {
extraHostNames = [ "rsb" "finaltask.xyz" "[finaltask.xyz]:2222" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIPTx8WBNNKBVRV98HgDChpd59SHbreJ87SXU+zOKan6y";
};
compute-deck = {
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIGt43GmXCxkl5QjgPQ/QimW11lKfXmV4GFWvlxQSf4TQ";
};
"2esrever" = {
extraHostNames = [ "10.4.5.218" "10.244.46.71" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIH0LnPrJxAdffZ//uRe3NBiIfFCBNMLqKVylkyU0llvT";
};
awoo = {
extraHostNames = [ "45.142.157.71" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOQaDjjfSK8jnk9aFIiYH9LZO4nLY/oeAc7BKIPUXMh1";
};
deckvacu = {
publicKey = "ecdsa-sha2-nistp256 AAAAE2VjZHNhLXNoYTItbmlzdHAyNTYAAAAIbmlzdHAyNTYAAABBBEa8qpFkIlLLJkH8rmEAn6/MZ9ilCGmEQWC3CeFae7r1kOqfwRk0nq0oyOGJ50uIh+PpwEh3rbgq6mLfpRfsFmM=";
};
liam = {
extraHostNames = [ "liam.dis8.net" "178.128.79.152" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIHOqJYVHOIFmEA5uRbbirIupWvyBLAFwic/8EZQRdN/c";
};
devver = {
extraHostNames = [ "devver.t2d.lan" "10.78.79.10" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFeFaH2tzWIiCPdKNmxl3NqCnPTdmVIOBinauUAEl+UU";
};
fw = {
extraHostNames = [ "fw.t2d.lan" ];
publicKey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIA6lX25mCy35tf1NpcHMAdeRgvT7l0Dw0FWBH3eX4TE2";
};
};
};
}

View File

@@ -1,16 +1,22 @@
{ config, ... }:
{
imports = [
./module.nix
./commands.nix
./common-but-not.nix
];
config,
lib,
vacuModuleType,
...
}:
let
inherit (lib) mkDefault;
in
lib.optionalAttrs (vacuModuleType == "nix-on-droid") {
environment.packages = config.vacu.packageList;
environment.etc."ssh/ssh_config".text = config.vacu.ssh.config;
nix.substituters = config.vacu.nix.extraSubstituters;
nix.trustedPublicKeys = config.vacu.nix.extraTrustedKeys;
nix.substituters = lib.mkForce config.vacu.nix.substituterUrls;
nix.trustedPublicKeys = lib.mkForce config.vacu.nix.trustedKeys;
vacu.shell.functionsDir = "${config.user.home}/.nix-profile/share/vacufuncs";
environment.etc.bashrc.text = config.vacu.shell.interactiveLines;
environment.etc.profile.text = config.vacu.shell.interactiveLines;
environment.etc."vacu.json".text = builtins.toJSON config.vacu.versionInfo;
environment.etc."vacu/info.json".text = builtins.toJSON config.vacu.versionInfo;
vacu.hostName = mkDefault "nix-on-droid";
vacu.shortHostName = mkDefault "nod";
}

36
common/nix.nix Normal file
View File

@@ -0,0 +1,36 @@
{ lib, config, ... }:
let
inherit (lib) mkOption types;
caches = builtins.attrValues config.vacu.nix.caches;
enabledCaches = builtins.filter (c: c.enable) caches;
in
{
options = {
vacu.nix.caches = mkOption {
type = types.attrsOf (
types.submodule (
{ name, ... }:
{
options = {
url = mkOption { type = types.str; };
keys = mkOption {
type = types.listOf types.str;
default = [ ];
};
enable = mkOption {
default = true;
type = types.bool;
};
};
}
)
);
};
vacu.nix.substituterUrls = mkOption { readOnly = true; };
vacu.nix.trustedKeys = mkOption { readOnly = true; };
vacu.nix.plainOptions = mkOption { };
};
config.vacu.nix.substituterUrls = map (c: c.url) enabledCaches;
config.vacu.nix.trustedKeys = builtins.concatMap (c: c.keys) enabledCaches;
config.vacu.nix.plainOptions.allowUnfree = true;
}

34
common/nixos-rebuild.nix Normal file
View File

@@ -0,0 +1,34 @@
{
pkgs,
config,
lib,
vacuModuleType,
...
}:
let
nixos-rebuild = pkgs.nixos-rebuild.override { nix = config.nix.package.out; };
in
lib.optionalAttrs (vacuModuleType == "nixos") {
options.vacu.alwaysUseRemoteSudo =
(lib.mkEnableOption "always deploy to this machine with --use-remote-sudo")
// {
default = true;
};
config = lib.mkIf config.vacu.alwaysUseRemoteSudo {
system.build.nixos-rebuild = lib.mkForce (
pkgs.runCommandLocal "nixos-rebuild-wrapped"
{
nativeBuildInputs = [ pkgs.makeShellWrapper ];
meta.mainProgram = "nixos-rebuild";
}
''
runHook preInstall
mkdir -p $out/bin
makeShellWrapper ${lib.getExe nixos-rebuild} $out/bin/nixos-rebuild --add-flags "--use-remote-sudo"
runHook postInstall
''
);
};
}

View File

@@ -1,61 +1,55 @@
{ lib, pkgs, config, inputs, utils, ... }:
{
imports = [ ./module.nix ./commands.nix ./common-but-not.nix ];
lib,
pkgs,
config,
vacuModuleType,
...
}:
lib.optionalAttrs (vacuModuleType == "nixos") {
options.vacu.underTest = lib.mkOption {
default = false;
type = lib.types.bool;
};
options.vacu.acmeCertDependencies = lib.mkOption {
default = {};
example = ''
vacu.acmeCertDependencies."mail.example.com" = [ "postfix.service" ];
'';
type = lib.types.attrsOf (lib.types.listOf utils.systemdUtils.lib.unitNameType);
};
config = let
for-systemd-services = lib.concatMapAttrs
(cert: units:
{
"acme-selfsigned-${cert}" = {
wantedBy = units;
before = units;
};
}
)
config.vacu.acmeCertDependencies;
for-security-acme-certs = lib.concatMapAttrs
(cert: units:
{
${cert}.reloadServices = units;
}
)
config.vacu.acmeCertDependencies;
in {
config = {
# the security warning might as well have said "its insecure maybe but there's nothing you can do about it"
# presumably needed by nheko
nixpkgs.config.permittedInsecurePackages = [ "olm-3.2.16" ];
# nixpkgs.overlays = [ inputs.self.overlays.default ];
console = {
keyMap = lib.mkDefault "us";
};
networking = if config.vacu.hostName == null then { } else { hostName = config.vacu.hostName; };
vacu.packages."xorg-xev" = {
enable = config.services.xserver.enable;
package = pkgs.xorg.xev;
};
environment.systemPackages = config.vacu.packageList;
programs.git = {
enable = true;
lfs.enable = true;
programs.nix-ld.enable = true;
system.nixos.tags = [
"vacu${config.vacu.versionId}"
config.vacu.hostName
];
environment.etc."vacu/info.json".text = builtins.toJSON config.vacu.versionInfo;
environment.etc."chromium" = lib.mkIf (config.vacu.systemKind == "desktop") {
source = "/run/current-system/sw/etc/chromium";
};
system.nixos.tags = [ "vacu${config.vacu.versionId}" ];
environment.etc."vacu.json".text = builtins.toJSON config.vacu.versionInfo;
i18n.defaultLocale = lib.mkDefault "en_US.UTF-8";
time.timeZone = "America/Los_Angeles";
users.users.shelvacu = {
openssh.authorizedKeys.keys = config.vacu.ssh.authorizedKeys;
users.users.shelvacu = lib.mkIf (config.vacu.systemKind != "container") {
openssh.authorizedKeys.keys = lib.attrValues config.vacu.ssh.authorizedKeys;
isNormalUser = true;
extraGroups = [ "wheel" ];
};
systemd.services = for-systemd-services;
security.acme.certs = for-security-acme-certs;
# # safety user: if something is super fucked up with my shell stuff, I can ssh in as shelvac2
# users.users.shelvac2 = {
# openssh.authorizedKeys.keys = config.vacu.ssh.authorizedKeys;
# isNormalUser = true;
# extraGroups = [ "wheel" ];
# shell = pkgs.bash;
# };
services.openssh = {
# require public key authentication for better security
settings.PasswordAuthentication = false;
@@ -63,37 +57,48 @@
settings.PermitRootLogin = "prohibit-password";
};
nix.settings.trusted-users = [ "shelvacu" ];
nix.settings.trusted-users = lib.mkIf (config.vacu.systemKind != "container") [ "shelvacu" ];
security.sudo.wheelNeedsPassword = lib.mkDefault false;
programs.screen = {
enable = true;
screenrc = ''
defscrollback 10000
termcapinfo xterm* ti@:te@
maptimeout 5
maptimeout 5
'';
} // (if config.system.nixos.release == "23.11" then {} else { enable = true; });
};
programs.tmux.enable = true;
programs.tmux.extraConfig = "setw mouse";
programs.tmux.clock24 = true;
programs.tmux = lib.mkIf (config.vacu.systemKind != "container") {
enable = true;
extraConfig = "setw mouse";
clock24 = true;
};
nix.settings = {
experimental-features = [ "nix-command" "flakes" ];
substituters = config.vacu.nix.extraSubstituters;
trusted-public-keys = config.vacu.nix.extraTrustedKeys;
experimental-features = [
"nix-command"
"flakes"
];
substituters = lib.mkForce config.vacu.nix.substituterUrls;
extra-substituters = lib.mkForce [ ];
trusted-public-keys = lib.mkForce config.vacu.nix.trustedKeys;
extra-trusted-public-keys = lib.mkForce [ ];
};
nixpkgs.config.allowUnfree = lib.mkDefault true;
programs.mosh.enable = lib.mkDefault true;
programs.mosh.enable = lib.mkIf (config.vacu.systemKind != "container") (lib.mkDefault true);
programs.ssh.extraConfig = config.vacu.ssh.config;
security.pki.certificates = config.vacu.rootCAs;
# commands.nix
environment.pathsToLink = [ "/share/vacufuncs" ];
vacu.shell.functionsDir = "/run/current-system/sw/share/vacufuncs";
environment.pathsToLink = [
"/share/vacufuncs"
"/etc/chromium"
];
programs.bash.interactiveShellInit = config.vacu.shell.interactiveLines;
programs.bash.promptInit = lib.mkForce "";
};
}

17
common/nixvim.nix Normal file
View File

@@ -0,0 +1,17 @@
{
pkgs,
config,
inputs,
lib,
...
}:
{
vacu.nixvimPkg = inputs.self.packages.${pkgs.system}.nixvim;
vacu.shell.functions =
lib.mkIf (config.vacu.systemKind != "minimal" && config.vacu.systemKind != "container")
{
nvim-plain = ''${pkgs.neovim}/bin/nvim "$@"'';
nvim-nixvim = ''${config.vacu.nixvimPkg}/bin/nvim "$@"'';
nvim = ''nvim-nixvim "$@"'';
};
}

View File

@@ -1,34 +0,0 @@
# These are the things that might in a simpler time go in ~/.bashrc as aliases. But they're not aliases, cuz aliases are bad
{ pkgs, vaculib, ... }: let
inherit (pkgs) writeScriptBin;
inherit (vaculib) writeShellFunction;
in {
vacu.packages = [
(writeScriptBin "ms" ''
set -e
if [[ $# != 1 ]]; then
echo "wrong number of args" 1>&2
exit 1
fi
set -x
mosh -- $1 sudo screen -Rd
'')
(writeScriptBin "rmln" ''
set -eo pipefail
for arg in "$@"; do
if [[ "$arg" != "-*" ]] && [[ ! -L "$arg" ]]; then
echo "$0: $arg is not a symlink" 1>&2
exit 1
fi
done
rm $@
'')
(writeShellFunction "nd" ''
declare -a args
args=("$@")
mkdir "''${args[@]}" && cd "''${args[-1]}"
'')
(writeShellFunction "td" ''pushd $(mktemp "$@")'')
];
}

View File

@@ -1,34 +1,65 @@
{ config, pkgs, lib, ... }: let
{
config,
pkgs,
lib,
...
}:
let
inherit (lib) mkOption types;
pkgOptions = builtins.attrValues config.vacu.packages;
enabledOptions = builtins.filter (o: o.enable) pkgOptions;
enabledPkgs = builtins.map (o: o.package) enabledOptions;
packagesSetType = types.attrsOf (types.submodule ({ name, config, options, ... }: {
options = {
enable = mkOption {
type = types.bool;
description = "Will this package be installed (included in environment.systemPackages)";
};
package = mkOption {
type = types.package;
default = pkgs.${name};
defaultText = "pkgs.${name}";
};
};
}));
packageListToSet = (from: let
keyvals = map (val:
if builtins.isString val then
{ name = val; value = { package = pkgs."${val}"; enable = lib.mkDefault true; }; }
else
{ name = val.name; value = { package = val; enable = lib.mkDefault true; }; }
) from;
in builtins.listToAttrs keyvals);
in {
packagesSetType = types.attrsOf (
types.submodule (
{ name, ... }:
{
options = {
enable = mkOption {
type = types.bool;
description = "Will this package be installed (included in environment.systemPackages)";
};
package = mkOption {
type = types.package;
default = pkgs.${name};
defaultText = "pkgs.${name}";
};
};
}
)
);
packageListToSet = (
from:
let
keyvals = map (
val:
if builtins.isString val then
{
name = val;
value = {
package = pkgs."${val}";
enable = lib.mkDefault true;
};
}
else
{
name = val.pname or val.name;
value = {
package = lib.mkDefault val;
enable = lib.mkDefault true;
};
}
) from;
in
builtins.listToAttrs keyvals
);
in
{
options = {
vacu.packages = mkOption {
default = {};
type = types.coercedTo (types.listOf (types.either types.str types.package)) packageListToSet packagesSetType;
default = { };
type = types.coercedTo (types.listOf (
types.either types.str types.package
)) packageListToSet packagesSetType;
};
vacu.packageList = mkOption {
type = types.listOf types.package;

35
common/remapCapsLock.nix Normal file
View File

@@ -0,0 +1,35 @@
{
pkgs,
lib,
config,
vacuModuleType,
...
}:
let
inherit (lib) mkOption types;
in
lib.optionalAttrs (vacuModuleType == "nixos") {
options.vacu.enableCapsLockRemap = mkOption {
type = types.bool;
default = config.vacu.systemKind == "desktop";
};
config = lib.mkIf config.vacu.enableCapsLockRemap {
# https://discourse.nixos.org/t/best-way-to-remap-caps-lock-to-esc-with-wayland/39707/6
services.interception-tools =
let
itools = pkgs.interception-tools;
itools-caps = pkgs.interception-tools-plugins.caps2esc;
in
{
enable = true;
plugins = [ itools-caps ];
# requires explicit paths: https://github.com/NixOS/nixpkgs/issues/126681
udevmonConfig = pkgs.lib.mkDefault ''
- JOB: "${itools}/bin/intercept -g $DEVNODE | ${itools-caps}/bin/caps2esc -m 1 | ${itools}/bin/uinput -d $DEVNODE"
DEVICE:
EVENTS:
EV_KEY: [KEY_CAPSLOCK, KEY_ESC]
'';
};
};
}

55
common/repos-impl.nix Normal file
View File

@@ -0,0 +1,55 @@
{
config,
lib,
vacuModuleType,
...
}:
{
imports = [
(lib.optionalAttrs (vacuModuleType == "nixos") {
config.vacu.repos.path = lib.mkIf (config.users.users ? shelvacu) (lib.mkDefault "${config.users.users.shelvacu.home}/dev");
})
(lib.optionalAttrs (vacuModuleType == "nix-on-droid") {
config.vacu.repos.path = lib.mkDefault "${config.user.home}";
})
];
vacu.repos = {
enable = lib.mkDefault true;
forges.uninsane.baseUrl = "git@git.uninsane.org:";
forges.github.baseUrl = "git@github.com";
forges.gitlab.basrUrl = "git@gitlab.com";
defaultOrigin = "uninsane";
repos.colin-nix-files = {
owner = "colin";
repoName = "nix-files";
origin = "uninsane";
};
# gh:Isaac0-dev/coopnet
repos.coopnet = {
owner = "Isaac0-dev";
origin = "github";
};
repos.metadl = {};
repos.nixos-apple-silicon = {
origin = "github";
owner = "tpwrules";
};
repos.nixpkgs = {
origin = "github";
owner = "nixos";
remotes = [
{
forge = "uninsane";
owner = "colin";
}
];
};
repos.nix-stuff = {};
repos.numberlink-solver = {};
repos.sm64coopdx = {
origin = "github";
owner = "coop-deluxe";
};
};
}

132
common/repos-options.nix Normal file
View File

@@ -0,0 +1,132 @@
{
lib,
config,
vaculib,
...
}:
let
inherit (lib) mkOption types;
cfg = config.vacu.repos;
forgeModule = {
name,
config,
...
}: {
options = {
name = mkOption {
type = types.str;
default = name;
};
remoteName = mkOption {
type = types.str;
default = config.name;
};
url = mkOption {
type = types.str;
};
};
};
remoteModule = {
name,
config,
...
}: {
options = {
name = mkOption { type = types.str; default = name; };
baseUrl = mkOption { type = types.str; };
path = mkOption { type = types.str; };
url = mkOption { type = types.str; default = config.baseUrl + config.path; };
};
};
repoModule = let outercfg = cfg; in {
name,
config,
...
}:
let
remoteType = (
types.coercedTo
types.str
(from: { name = from; baseUrl = config.vacu.repos.forges.${from}.url; })
(types.subModuleWith {
modules = [
remoteModule
{
config.path = lib.mkDefault config.remotePath;
}
];
})
);
in
{
options = {
name = mkOption {
type = types.str;
default = name;
};
localDir = mkOption {
type = types.strMatching "[^/]+";
default = config.name;
};
localPath = mkOption {
type = types.path;
default = "${outercfg.path}/${config.localDir}";
};
owner = mkOption {
type = types.str;
default = "shelvacu";
};
remoteName = mkOption {
type = types.str;
default = config.name;
};
remotePath = mkOption {
type = types.str;
default = "${config.owner}/${config.remoteName}";
};
origin = mkOption {
type = remoteType;
};
remotes = mkOption {
type = types.listOf remoteType;
default = [];
};
};
};
in
{
imports = [
# (vaculib.assertNoDuplicatesModule "vacu.repos" "name")
# (vaculib.assertNoDuplicatesModule "vacu.repos" "localPath")
];
options.vacu.repos = {
enable = lib.mkEnableOption "manage repos";
path = mkOption {
type = types.path;
};
defaultOrigin = mkOption { type = types.str; };
forges = mkOption {
default = {};
type = types.attrsOf (types.submoduleWith {
modules = [ forgeModule ];
});
};
repos = mkOption {
type = types.attrsOf (types.submoduleWith { modules = [
repoModule
{ config.origin = cfg.defaultOrigin; }
]; });
default = {};
};
};
}

193
common/shell/default.nix Normal file
View File

@@ -0,0 +1,193 @@
{
config,
lib,
pkgs,
vaculib,
...
}:
let
inherit (lib) mkOption types;
cfg = config.vacu.shell;
writeShellFunction =
name: text:
pkgs.writeTextFile {
inherit name;
executable = false;
destination = "/share/vacufuncs/${name}";
text = ''
${text}
'';
checkPhase = ''
${pkgs.stdenv.shellDryRun} "$target"
'';
};
functionPackages = lib.mapAttrsToList writeShellFunction cfg.functions;
vacuInitFile = pkgs.writeText "vacu.shell.interactiveLines.sh" cfg.interactiveLines;
wrappedBashPkg = vaculib.makeWrapper {
original = pkgs.bash;
new = "vacuinit-bash";
prepend_flags = [
"--init-file"
vacuInitFile
];
};
wrappedBash = lib.getExe wrappedBashPkg;
in
{
imports = [
./not-aliases.nix
./ps1.nix
];
options = {
vacu.shell.functionsDir = mkOption {
type = types.path;
default = "/run/current-system/sw/share/vacufuncs";
};
vacu.shell.interactiveLines = mkOption {
type = types.lines;
readOnly = true;
};
vacu.shell.wrappedBash = mkOption {
readOnly = true;
};
vacu.shell.idempotentShellLines = mkOption {
type = types.lines;
default = "";
};
vacu.shell.color = mkOption {
type = types.enum (builtins.attrNames vaculib.shellColors);
default = "white";
};
vacu.shell.functions = mkOption {
type = types.attrsOf types.str;
};
};
config.vacu = {
vaculib = {
# https://en.wikipedia.org/wiki/ANSI_escape_code#Colors
shellColors = {
black = 30;
red = 31;
green = 32;
yellow = 33;
blue = 34;
magenta = 35;
cyan = 36;
white = 37;
};
};
shell.interactiveLines = ''
if [[ $- == *i* ]] && [[ -f ${cfg.functionsDir}/vacureload ]]; then
function __vacushell_load() { eval "$(cat ${cfg.functionsDir}/vacureload)"; }
__vacushell_load
unset __vacushell_load
fi
'';
shell.wrappedBash = wrappedBash;
shell.functions = {
"vacureload" = ''
declare -gA vacuShellFunctionsLoaded
if ! [[ -f ${cfg.functionsDir}/vacureload ]]; then
echo "vacureload: I think that's my cue to leave (${cfg.functionsDir}/vacureload not found, assuming vacureload-less config has been loaded and unloading myself)" 1>&2
for funcname in "''${!vacuShellFunctionsLoaded[@]}"; do
unset -f $funcname
done
return
fi
for funcname in "''${!vacuShellFunctionsLoaded[@]}"; do
if ! [[ -f ${cfg.functionsDir}/$funcname ]]; then
unset -f $funcname
fi
done
for fullPath in ${cfg.functionsDir}/*; do
local funcname="$(basename "$fullPath")"
local followedPath="$(readlink -f "$fullPath")"
if [[ "''${vacuShellFunctionsLoaded[$funcname]}" != "$followedPath" ]]; then
unset -f $funcname
eval "function ''${funcname}() { if [[ -f '$fullPath' ]]; then eval "'"$'"(cat '$fullPath')"'"'"; else echo '$funcname is no longer there, kindly removing myself.' 1>&2; unset $funcname; return 1; fi }"
vacuShellFunctionsLoaded[$funcname]=$followedPath
fi
unset followedPath
unset funcname
done
__set_idempotents
'';
"__set_idempotents" = cfg.idempotentShellLines;
vhich = ''
if [[ $# != 1 ]]; then
echo "expected exactly one arg" 1>&2
return 1
fi
query="$1"
quote='`'"$query'"
kind="$(type -t "$query")"
if [[ "$kind" == "" ]]; then
echo "could not find any command $quote" 1>&2
return 1
fi
echo "$quote is a $kind"
case "$kind" in
"alias")
alias "$query"
return 0
;;
"keyword")
echo "See https://www.gnu.org/software/bash/manual/html_node/Reserved-Word-Index.html"
return 0
;;
"function")
if [[ -v vacuShellFunctionsLoaded["$query"] ]]; then
echo "$quote is a vacufunc"
path="''${vacuShellFunctionsLoaded[$query]}"
# continue to below
else
declare -f "$query"
return 0
fi
;;
"builtin")
echo "Docs: https://www.gnu.org/software/bash/manual/html_node/Bash-Builtins.html#index-$query"
return 0
;;
"file")
path="$(which "$query")"
# continue to below
;;
*)
echo 'ERR: unexpected return from `type -t`: '"$kind" 1>&2
return 1
esac
echo "path:"
while [[ -L "$path" ]]; do
dest="$(readlink "$path")"
echo " $path is a symlink to $dest"
if [[ "$dest" != /* ]]; then
dest="$(dirname "$path")/$dest"
fi
path="$dest"
done
echo " $path"
if ! [[ -e "$path" ]]; then
echo "$path does not exist!"
return 1
fi
canon="$(readlink -f "$path")"
if [[ "$path" != "$canon" ]]; then
echo " $path canonicalizes to $canon"
path="$canon"
fi
magic_parse="$(file --brief --mime "$path")"
echo "magic: $magic_parse"
case "$magic_parse" in
'text/x-shellscript;'* | 'text/plain;'*)
echo "initial contents:"
echo
cat "$path" | head --lines=10 | head --bytes=2000
echo "..."
;;
esac
'';
};
packages = functionPackages;
};
}

View File

@@ -0,0 +1,101 @@
# These are the things that might in a simpler time go in ~/.bashrc as aliases. But they're not aliases, cuz aliases are bad
{ pkgs, lib, ... }:
let
inherit (pkgs) writeScriptBin;
ms_text = with_sudo: ''
set -eo pipefail
if [[ $# -gt 3 ]] || [[ $# == 0 ]]; then
echo "wrong number of args" 1>&2
exit 1
fi
host="$1"
session_name="''${2:-main}"
set -x
mosh -- "$host" ${lib.optionalString with_sudo "sudo"} screen -RdS "$session_name"
'';
msl_text = ''
set -eo pipefail
if [[ $# != 1 ]]; then
echo "wrong number of args" 1>&2
exit 1
fi
host="$1"
echo 'echo "user:"; screen -ls; echo; echo "root:"; sudo screen -ls' | ssh -T "$host"
'';
in
{
vacu.packages = [
(writeScriptBin "ms" (ms_text false))
(writeScriptBin "mss" (ms_text true))
(writeScriptBin "msl" msl_text)
(writeScriptBin "rmln" ''
set -eo pipefail
for arg in "$@"; do
if [[ "$arg" != "-*" ]] && [[ ! -L "$arg" ]]; then
echo "$0: $arg is not a symlink" 1>&2
exit 1
fi
done
rm "$@"
'')
(writeScriptBin "nr" ''
# nix run nixpkgs#<thing> -- <args>
set -eo pipefail
if [[ $# == 0 ]]; then
echo "need at least one arg" 1>&2
exit 1
fi
installable="$1"
shift
if [[ "$installable" != *'#'* ]]; then
installable="nixpkgs#$installable"
fi
nix run "$installable" -- "$@"
'')
(writeScriptBin "nb" ''
# nix build nixpkgs#<thing> <args>
set -eo pipefail
if [[ $# == 0 ]]; then
echo "need at least one arg" 1>&2
exit 1
fi
installable="$1"
shift
if [[ "$installable" != *'#'* ]]; then
installable="nixpkgs#$installable"
fi
nix build "$installable" "$@"
'')
(writeScriptBin "ns" ''
# nix shell nixpkgs#<thing>
set -eo pipefail
new_args=( )
for arg in "$@"; do
if [[ "$arg" != *'#'* ]] && [[ "$arg" != -* ]]; then
arg="nixpkgs#$arg"
fi
new_args+=("$arg")
done
nix shell "''${new_args[@]}"
'')
];
vacu.shell.functions = {
nd = ''
declare -a args
args=("$@")
lastarg="''${args[-1]}"
if [[ "$lastarg" == "-*" ]]; then
echo "$0: last argument must be the directory" 1>&2
return 1
fi
for arg in "''${args[@]::''${#args[@]}-1}}"; do
if [[ "$arg" != "-*" ]]; then
echo "$0: last argument must be the directory" 1>&2
return 1
fi
done
mkdir "''${args[@]}" && cd "''${args[-1]}"
'';
nt = ''pushd $(mktemp -d "$@")'';
};
}

77
common/shell/ps1.nix Normal file
View File

@@ -0,0 +1,77 @@
{
config,
lib,
vaculib,
vacuModuleType,
...
}:
let
cfg = config.vacu.shell;
# https://en.wikipedia.org/wiki/ANSI_escape_code#Colors
colors = vaculib.shellColors;
# TODO: reset_without_clear doesn't fully work
# thanks colin https://git.uninsane.org/colin/nix-files/src/commit/7f5b2628016c8ca1beec417766157c7676a9c5e5/hosts/common/programs/zsh/starship.nix#L24
set = opt: ''\e[?${opt}h'';
clear = opt: ''\e[?${opt}l'';
reset_without_clear = builtins.concatStringsSep "" [
# reset terminal mode (in case the previous command screwed with it)
# 'l' = turn option of, 'h' = turn option on.
#
# options are enumerated in Alacritty's VTE library's `PrivateMode` type:
# - <https://github.com/alacritty/vte/blob/ebc4a4d7259678a8626f5c269ea9348dfc3e79b2/src/ansi.rs#L845>
# see also the reset code path (does a bit too much, like clearing the screen):
# - <https://github.com/alacritty/alacritty/blob/6067787763e663bd308e5b724a5efafc2c54a3d1/alacritty_terminal/src/term/mod.rs#L1802>
# and the crucial TermMode::default: <https://github.com/alacritty/alacritty/blob/master/alacritty_terminal/src/term/mod.rs#L113>
#
# query the state of any mode bit `<n>` with `printf '\033[?<n>$p'`
# e.g. `printf '\033[?7$p'` returns `^[[?7;1$y` with the `1` indicating it's **set**,
# `printf '\033[?1000$p'` returns `^[[?1000;2$y` with the `2` indicating it's **unset**.
#
# TODO: unset Line mode and Insert mode?
(clear "1") # Cursor Keys
# (clear "3") # Column Mode (i.e. clear screen/history)
(clear "6") # Origin
(set "7") # Line Wrap
(clear "12") # Blinking Cursor
(set "25") # Show Cursor
(clear "1000") # Report Mouse Clicks
(clear "1002") # Report Cell Mouse Motion
(clear "1003") # Report All Mouse Motion
(clear "1004") # Report Focus In/Out
(clear "1005") # UTF8 Mouse
(clear "1006") # Sgr Mouse
(set "1007") # Alternate Scroll
(set "1042") # Urgency Hints
# (clear "1049") # Swap Screen And Set Restore Cursor
(clear "2004") # Bracketed Paste
(clear "2026") # Sync Update
];
# https://man.archlinux.org/man/bash.1#PROMPTING
# \[ and \] begins and ends "a sequence of non-printing characters"
set_color = colornum: ''\[\e[1;${toString colornum}m\]'';
set_inverted_color = colornum: ''\[\e[1;37;${toString (colornum + 10)}m\]'';
reset_color = ''\[\e[0m\]'';
colornum = colors.${cfg.color};
root_text = root: lib.optionalString root "ROOT@";
final = root: if root then (set_inverted_color colors.red) + "!!" else "$";
hostName = if vacuModuleType == "plain" then ''\h'' else config.vacu.shortHostName;
default_ps1 =
root:
''\n''
# + ''\[${reset_without_clear}\]''
+ (set_color colornum)
+ ''${root_text root}${hostName}:\w''
+ (final root)
+ reset_color
+ " ";
in
{
vacu.shell.idempotentShellLines = ''
if [ $UID = 0 ]; then
export PS1=${lib.escapeShellArg (default_ps1 true)}
else
export PS1=${lib.escapeShellArg (default_ps1 false)}
fi
'';
}

54
common/sops.nix Normal file
View File

@@ -0,0 +1,54 @@
{
lib,
pkgs,
config,
vaculib,
...
}:
let
userKeys = lib.attrValues config.vacu.ssh.authorizedKeys;
liamKey = config.vacu.ssh.knownHosts.liam.publicKey;
ssh-to-age = lib.getExe pkgs.ssh-to-age;
sopsConfig =
pkgs.runCommand "sops.yaml" { env.sshUserKeys = lib.concatStringsSep "\n" userKeys; }
''
set -e
liamKey="$(echo "${liamKey}" | ${ssh-to-age})"
declare -a userKeys
mapfile -t userKeys < <(echo "$sshUserKeys" | ${ssh-to-age})
declare -p userKeys
cat <<END >> $out
creation_rules:
- path_regex: secrets/misc/[^/]+$
key_groups:
- age: [$(printf '"%s", ' "''${userKeys[@]}")]
- path_regex: secrets/liam/[^/]+$
key_groups:
- age: ["$liamKey",$(printf '"%s", ' "''${userKeys[@]}")]
- path_regex: /tests/test_secrets/
key_groups:
- age: ["age1eqv5759uknu7d46rqyyzsmgt43qumsge3makeWrapp3yp2xygapprnt8zu3sqx6kt8w"]
END
'';
testAgeSecret = "AGE-SECRET-KEY-1QQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQPQQ94XCHF";
wrappedSops = vaculib.makeWrapper {
original = lib.getExe pkgs.sops;
new = "vacu-nix-stuff-sops";
add_flags = [
"--config"
sopsConfig
];
run = lib.singleton ''
set -e
age_keys=("${testAgeSecret}" "$(cat $HOME/.ssh/id_ed25519 | ${lib.getExe pkgs.ssh-to-age} -private-key)")
export SOPS_AGE_KEY
printf -v SOPS_AGE_KEY "%s\n" "''${age_keys[@]}"
# declare -p SOPS_AGE_KEY
'';
};
in
{
options.vacu.sopsConfig = vaculib.mkOutOption sopsConfig;
options.vacu.wrappedSops = vaculib.mkOutOption wrappedSops;
}

51
common/sourceTree.nix Normal file
View File

@@ -0,0 +1,51 @@
{
inputs,
pkgs,
lib,
config,
vacuModuleType,
...
}:
let
inherit (builtins) isString isAttrs;
inherit (lib) mkOption types;
traverseInputs =
linkDir: unfilteredInputs:
assert isString linkDir;
assert isAttrs unfilteredInputs;
let
inputs = removeAttrs unfilteredInputs [ "self" ];
in
lib.concatStringsSep "\n" (
lib.mapAttrsToList (
inputName: inputAttrs:
let
thisDir = linkDir + "/" + inputName;
in
assert isAttrs inputAttrs;
assert isAttrs (inputAttrs.inputs or { });
''
mkdir -p ${thisDir}
ln -s ${inputAttrs} ${thisDir}/self
${traverseInputs thisDir (inputAttrs.inputs or { })}
''
) inputs
);
in
{
options.vacu.sourceTree = mkOption {
readOnly = true;
type = types.package;
};
config =
{
vacu.sourceTree = pkgs.runCommand "inputs-tree" { } ''
mkdir -p $out
ln -s ${inputs.self} $out/self
${traverseInputs "$out" inputs}
'';
}
// (lib.optionalAttrs (vacuModuleType == "nixos" || vacuModuleType == "nix-on-droid") {
environment.etc."vacu/sources".source = "${config.vacu.sourceTree}";
});
}

View File

@@ -1,90 +1,120 @@
{ pkgs, lib, config, ... }: let
inherit (lib) mkOption types flip concatMapStringsSep optionalString concatStringsSep readFile mapAttrsToList literalExpression;
{
lib,
config,
...
}:
let
inherit (lib)
mkOption
types
flip
concatMapStringsSep
optionalString
concatStringsSep
readFile
literalExpression
;
inherit (builtins) attrValues;
cfg = config.vacu;
knownHosts = attrValues cfg.ssh.knownHosts;
knownHostsText = (flip (concatMapStringsSep "\n") knownHosts
(h: assert h.hostNames != [];
optionalString h.certAuthority "@cert-authority " + concatStringsSep "," h.hostNames + " "
+ (if h.publicKey != null then h.publicKey else readFile h.publicKeyFile)
)) + "\n";
in {
knownHostsText =
(flip (concatMapStringsSep "\n") knownHosts (
h:
assert h.hostNames != [ ];
optionalString h.certAuthority "@cert-authority "
+ concatStringsSep "," h.hostNames
+ " "
+ (if h.publicKey != null then h.publicKey else readFile h.publicKeyFile)
))
+ "\n";
in
{
options = {
vacu.ssh.knownHostsText = mkOption {
type = types.str;
readOnly = true;
default = knownHostsText;
};
#vacu.ssh.authorizedKeys = mkOption { type = types.listOf types.str; };
vacu.ssh.authorizedKeys = mkOption {
type = types.listOf types.str;
};
vacu.ssh.config = mkOption {
type = types.lines;
type = types.attrsOf types.str;
default = { };
};
vacu.ssh.config = mkOption { type = types.lines; };
# Straight copied from nixpkgs
# https://github.com/NixOS/nixpkgs/blob/46397778ef1f73414b03ed553a3368f0e7e33c2f/nixos/modules/programs/ssh.nix
vacu.ssh.knownHosts = mkOption {
default = {};
type = types.attrsOf (types.submodule ({ name, config, options, ... }: {
options = {
certAuthority = mkOption {
type = types.bool;
default = false;
description = ''
This public key is an SSH certificate authority, rather than an
individual host's key.
'';
};
hostNames = mkOption {
type = types.listOf types.str;
default = [ name ] ++ config.extraHostNames;
defaultText = literalExpression "[ ${name} ] ++ config.${options.extraHostNames}";
description = ''
A list of host names and/or IP numbers used for accessing
the host's ssh service. This list includes the name of the
containing `knownHosts` attribute by default
for convenience. If you wish to configure multiple host keys
for the same host use multiple `knownHosts`
entries with different attribute names and the same
`hostNames` list.
'';
};
extraHostNames = mkOption {
type = types.listOf types.str;
default = [];
description = ''
A list of additional host names and/or IP numbers used for
accessing the host's ssh service. This list is ignored if
`hostNames` is set explicitly.
'';
};
publicKey = mkOption {
default = null;
type = types.nullOr types.str;
example = "ecdsa-sha2-nistp521 AAAAE2VjZHN...UEPg==";
description = ''
The public key data for the host. You can fetch a public key
from a running SSH server with the {command}`ssh-keyscan`
command. The public key should not include any host names, only
the key type and the key itself.
'';
};
publicKeyFile = mkOption {
default = null;
type = types.nullOr types.path;
description = ''
The path to the public key file for the host. The public
key file is read at build time and saved in the Nix store.
You can fetch a public key file from a running SSH server
with the {command}`ssh-keyscan` command. The content
of the file should follow the same format as described for
the `publicKey` option. Only a single key
is supported. If a host has multiple keys, use
{option}`programs.ssh.knownHostsFiles` instead.
'';
};
};
}));
default = { };
type = types.attrsOf (
types.submodule (
{
name,
config,
options,
...
}:
{
options = {
certAuthority = mkOption {
type = types.bool;
default = false;
description = ''
This public key is an SSH certificate authority, rather than an
individual host's key.
'';
};
hostNames = mkOption {
type = types.listOf types.str;
default = [ name ] ++ config.extraHostNames;
defaultText = literalExpression "[ ${name} ] ++ config.${options.extraHostNames}";
description = ''
A list of host names and/or IP numbers used for accessing
the host's ssh service. This list includes the name of the
containing `knownHosts` attribute by default
for convenience. If you wish to configure multiple host keys
for the same host use multiple `knownHosts`
entries with different attribute names and the same
`hostNames` list.
'';
};
extraHostNames = mkOption {
type = types.listOf types.str;
default = [ ];
description = ''
A list of additional host names and/or IP numbers used for
accessing the host's ssh service. This list is ignored if
`hostNames` is set explicitly.
'';
};
publicKey = mkOption {
default = null;
type = types.nullOr types.str;
example = "ecdsa-sha2-nistp521 AAAAE2VjZHN...UEPg==";
description = ''
The public key data for the host. You can fetch a public key
from a running SSH server with the {command}`ssh-keyscan`
command. The public key should not include any host names, only
the key type and the key itself.
'';
};
publicKeyFile = mkOption {
default = null;
type = types.nullOr types.path;
description = ''
The path to the public key file for the host. The public
key file is read at build time and saved in the Nix store.
You can fetch a public key file from a running SSH server
with the {command}`ssh-keyscan` command. The content
of the file should follow the same format as described for
the `publicKey` option. Only a single key
is supported. If a host has multiple keys, use
{option}`programs.ssh.knownHostsFiles` instead.
'';
};
};
}
)
);
description = ''
The set of system-wide known SSH hosts. To make simple setups more
convenient the name of an attribute in this set is used as a host name
@@ -107,10 +137,13 @@ in {
}
'';
};
config.assertions = lib.flip lib.mapAttrsToList config.vacu.ssh.knownHosts (name: data: {
assertion = (data.publicKey == null && data.publicKeyFile != null) ||
(data.publicKey != null && data.publicKeyFile == null);
message = "knownHost ${name} must contain either a publicKey or publicKeyFile";
});
};
config.vacu.assertions = lib.flip lib.mapAttrsToList config.vacu.ssh.knownHosts (
name: data: {
assertion =
(data.publicKey == null && data.publicKeyFile != null)
|| (data.publicKey != null && data.publicKeyFile == null);
message = "knownHost ${name} must contain either a publicKey or publicKeyFile";
}
);
}

34
common/units-config.nix Normal file
View File

@@ -0,0 +1,34 @@
{
vacu.units.extraUnits = {
b = "bit";
B = "byte";
kibi- = "1024";
Ki- = "kibi";
mebi- = "1024 kibi";
Mi- = "mebi";
gibi- = "1024 mebi";
Gi- = "gibi";
tebi- = "1024 gibi";
Ti- = "tebi";
pebi- = "1024 tebi";
Pi- = "pebi";
baud = "bit/s";
kbps = "kilobit/s";
kibps = "kibibit/s";
mbps = "megabit/s";
mibps = "mebibit/s";
gbps = "gigabit/s";
gibps = "gibibit/s";
tbps = "terabit/s";
tibps = "tebibit/s";
pbps = "petabit/s";
pibps = "pebibit/s";
month = "year/12";
mo = "month";
usd = "USD";
dollar = "USD";
cent = "0.01 USD";
"$" = "USD";
};
}

117
common/units-impl.nix Normal file
View File

@@ -0,0 +1,117 @@
{
config,
lib,
pkgs,
vaculib,
...
}:
let
inherit (lib) mkOption types;
unitNameRegex = let
# Unit names cannot begin or end with an underscore (_), a comma (,) or a decimal point (.). Names must not contain any of the operator characters +, -, *, /, |, ^, ;, ~, the comment character #, or parentheses. To facilitate copying and pasting from documents, several typographical characters are converted to operators: the figure dash (U+2012), minus (-; U+2212), and en dash (; U+2013) are converted to the operator -; the multiplication sign (×; U+00D7), N-ary times operator (U+2A09), dot operator (‘⋅’; U+22C5), and middle dot (‘·’; U+00B7) are converted to the operator *; the division sign (‘÷’; U+00F7) is converted to the operator /; and the fraction slash (U+2044) is converted to the operator |; accordingly, none of these characters can appear in unit names.
disallowedAnywhere = "+*/|^;~#()" + (builtins.fromJSON ''"\u2012\u2212\u2013\u00d7\u2a09\u22c5\u00b7\u00f7\u2044"'');
disallowedMiddle = "-" + disallowedAnywhere;
disallowedAtEnd = "23456789_,." + disallowedAnywhere;
disallowedAtBegin = "-01" + disallowedAtEnd;
anyExcept = chars: ''[^${lib.escapeRegex chars}]'';
singleChar = anyExcept disallowedAtBegin;
multiChar = ''${anyExcept disallowedAtBegin}${anyExcept disallowedMiddle}*${anyExcept disallowedAtEnd}'';
numberSuffix = regex: ''${regex}_[0-9\.,]+'';
fullRegex = ''${singleChar}|${multiChar}|${numberSuffix singleChar}|${numberSuffix multiChar}'';
in fullRegex;
unitsAttrsType = types.addCheck (types.attrsOf types.str) (attrs:
builtins.all (name: (builtins.match unitNameRegex name) != null) (builtins.attrNames attrs)
);
unitsDir = pkgs.stdenvNoCC.mkDerivation {
name = "vacu-units-files";
src = pkgs.units.src;
phases = [ "unpackPhase" "installPhase" ];
installPhase = ''
mkdir -p $out
cp {definitions,elements}.units $out
ln -s ${../units/currency.units} $out/currency.units
ln -s ${../units/cpi.units} $out/cpi.units
echo ${lib.escapeShellArg config.vacu.units.lines} > $out/vacu.units
'';
};
in
{
options.vacu.units = {
originalPackage = mkOption {
type = types.package;
default = pkgs.units;
};
finalPackage = mkOption {
type = types.package;
readOnly = true;
};
check = mkOption {
type = types.package;
readOnly = true;
};
generatedConfigDir = mkOption {
readOnly = true;
type = types.package;
};
generatedConfigFile = mkOption {
readOnly = true;
type = types.pathInStore;
};
lines = mkOption {
default = "";
type = types.lines;
};
extraUnits = mkOption {
type = unitsAttrsType;
default = {};
};
};
config = lib.mkMerge [
{
vacu.units = {
finalPackage = vaculib.makeWrapper {
original = config.vacu.units.originalPackage;
new = "units";
prepend_flags = [
"--file" config.vacu.units.generatedConfigFile
];
};
check = pkgs.runCommand "check-units" { } ''
# `units --check` returns success (exit code 0) regardless of success >:(
# example output:
# $ result/bin/units --check
# Currency exchange rates from exchangerate-api.com (USD base) on 2024-11-14
# Consumer price index data from US BLS, 2024-02-18
# 7247 units, 125 prefixes, 134 nonlinear units
#
output="$(${lib.getExe config.vacu.units.finalPackage} --check)"
echo "$output"
filteredLines="$(echo "$output" \
| grep -v '^\s*$' \
| grep -v 'Currency exchange rates from' \
| grep -v 'Consumer price index data from' \
| grep -vE '[0-9]+ units, [0-9]+ prefixes, [0-9]+ nonlinear units' || true
)"
if [[ -n "$filteredLines" ]]; then
exit 1
fi
touch $out
'';
generatedConfigDir = unitsDir;
generatedConfigFile = "${unitsDir}/vacu.units";
lines = lib.mkOrder 750 ''
# default units file, includes elements.units, currency.units, cpi.units
!include definitions.units
'';
};
}
{
vacu.units.lines = lib.concatStringsSep "\n" (lib.mapAttrsToList (name: value: "+${name}\t${value}") config.vacu.units.extraUnits);
}
];
}

View File

@@ -0,0 +1,63 @@
{
pkgs,
lib,
config,
...
}:
let
inherit (lib) mkOption mkEnableOption types;
cfg = config.vacu.verifySystem;
in
{
imports = [
./nixos.nix
];
options.vacu.verifySystem = {
enable = (mkEnableOption "verify system is what is expected") // {
default = true;
};
verifiers = mkOption {
default = { };
type = types.attrsOf (
types.submodule (
{ name, config, ... }:
{
options = {
enable = mkEnableOption "Enable system ident check ${name}";
name = mkOption {
type = types.str;
default = name;
};
script = mkOption {
type = types.lines;
default = "## system ident check ${config.name}";
};
};
}
)
);
};
verifyAllScript =
let
verifiers = (builtins.attrValues cfg.verifiers);
enabled = builtins.filter (s: s.enable) verifiers;
files = map (s: pkgs.writeText "vacu-verify-system-${s.name}.sh" s.script) enabled;
script = ''
## vacu verify-system
for f in ${lib.concatStringsSep " " files}; do
echo "verifying system with $f"
if ! source $f; then
echo "ERR: $f failed" >&2
return 1
fi
done
'';
scriptFile = pkgs.writeText "vacu-verify-system-all.sh" script;
in
mkOption {
readOnly = true;
default = scriptFile;
};
};
}

View File

@@ -0,0 +1,66 @@
{
lib,
config,
pkgs,
vacuModuleType,
...
}:
let
inherit (lib) mkOption types;
in
lib.optionalAttrs (vacuModuleType == "nixos") {
options.vacu.verifySystem.expectedMac = mkOption {
type = types.nullOr (types.strMatching "[A-Fa-f0-9]{2}(:[A-Fa-f0-9]{2}){5}");
default = null;
};
config = lib.mkIf config.vacu.verifySystem.enable {
# system.activationScripts."00-verify-system" = {
# text = "if ! source ${config.vacu.verifySystem.verifyAllScript}; then exit $?; fi";
# supportsDryActivation = true;
# };
system.extraSystemBuilderCmds = ''
mv $out/bin/switch-to-configuration $out/bin/.switch-to-configuration-unverified
cat <<EOF > $out/bin/switch-to-configuration
#!${pkgs.bash}/bin/bash
oldpath="$PATH"
export PATH="${pkgs.coreutils}/bin"
if ! source ${config.vacu.verifySystem.verifyAllScript}; then exit \$?; fi
export PATH="$oldpath"
exec $out/bin/.switch-to-configuration-unverified "\$@"
EOF
${pkgs.coreutils}/bin/chmod a+x $out/bin/switch-to-configuration
'';
vacu.verifySystem.verifiers = {
hostname = {
enable = lib.mkDefault config.vacu.verifySystem.expectedMac == null;
script = ''
expected=${config.networking.hostName}
actual=$(cat /proc/sys/kernel/hostname)
if [[ "$expected" != "$actual" ]]; then
echo "ERR: unexpected hostname; Trying to deploy to $expected but this is $actual" >&2
return 1
fi
'';
};
expectedMac = {
enable = config.vacu.verifySystem.expectedMac != null;
script = ''
expected=${lib.toUpper config.vacu.verifySystem.expectedMac}
declare -a actual=($(${pkgs.iproute2}/bin/ip -j link | ${pkgs.jq}/bin/jq 'map([.permaddr, .address] | map(strings | ascii_upcase)) | flatten | join("\n")' -r))
for ifMac in "''${actual[@]}"; do
if [[ "$ifMac" == "$expected" ]]; then
# all is well
return 0
fi
done
echo "ERR: Interface MAC address $expected not present, this may not be the system you intend to deploy to." >&2
echo " Found MAC addresses: ''${actual[*]}" >&2
return 1
'';
};
};
};
}

View File

@@ -1,6 +1,7 @@
{ ... }: {
hardware.bluetooth.enable = true;
hardware.bluetooth.powerOnBoot = true;
{ ... }:
{
hardware.bluetooth.enable = true;
hardware.bluetooth.powerOnBoot = true;
services.blueman.enable = true;
services.blueman.enable = true;
}

View File

@@ -1,4 +1,8 @@
{ config, pkgs, lib, jovian, inputs, ... }:
{
pkgs,
inputs,
...
}:
{
imports = [
@@ -10,9 +14,7 @@
./bluetooth.nix
./partitioning.nix
./padtype.nix
../common/nixos.nix
];
system.nixos.tags = [ "host-${config.networking.hostName}" ];
boot.loader.systemd-boot.enable = false;
boot.loader.efi.efiSysMountPoint = "/boot/EFI";
@@ -23,7 +25,10 @@
boot.binfmt.emulatedSystems = [ "aarch64-linux" ];
networking.hostName = "compute-deck";
vacu.hostName = "compute-deck";
vacu.shortHostName = "cd";
vacu.shell.color = "blue";
vacu.systemKind = "desktop";
networking.hostId = "e595d9b0";
boot.supportedFilesystems = [ "zfs" ];

View File

@@ -1,51 +1,60 @@
{ config, lib, pkgs, modulesPath, ... }:
{
config,
lib,
pkgs,
modulesPath,
...
}:
{
imports =
[ (modulesPath + "/installer/scan/not-detected.nix")
];
imports = [ (modulesPath + "/installer/scan/not-detected.nix") ];
boot.initrd.availableKernelModules = [ "nvme" "xhci_pci" "usbhid" "sdhci_pci" "dwc3_pci" ];
boot.initrd.availableKernelModules = [
"nvme"
"xhci_pci"
"usbhid"
"sdhci_pci"
"dwc3_pci"
];
boot.initrd.kernelModules = [ ];
boot.kernelModules = [ "kvm-amd" ];
boot.extraModulePackages = [ ];
/*
fileSystems."/" =
{ device = "/dev/disk/by-uuid/63f25199-ee0b-4991-8861-c3ba3b464ef2";
fsType = "btrfs";
options = [ "subvol=root" ];
};
/*
fileSystems."/" =
{ device = "/dev/disk/by-uuid/63f25199-ee0b-4991-8861-c3ba3b464ef2";
fsType = "btrfs";
options = [ "subvol=root" ];
};
fileSystems."/home" =
{ device = "/dev/disk/by-uuid/63f25199-ee0b-4991-8861-c3ba3b464ef2";
fsType = "btrfs";
options = [ "subvol=home" ];
};
fileSystems."/home" =
{ device = "/dev/disk/by-uuid/63f25199-ee0b-4991-8861-c3ba3b464ef2";
fsType = "btrfs";
options = [ "subvol=home" ];
};
fileSystems."/nix" =
{ device = "/dev/disk/by-uuid/63f25199-ee0b-4991-8861-c3ba3b464ef2";
fsType = "btrfs";
options = [ "subvol=nix" ];
};
fileSystems."/nix" =
{ device = "/dev/disk/by-uuid/63f25199-ee0b-4991-8861-c3ba3b464ef2";
fsType = "btrfs";
options = [ "subvol=nix" ];
};
fileSystems."/boot" =
{ device = "/dev/disk/by-uuid/63f25199-ee0b-4991-8861-c3ba3b464ef2";
fsType = "btrfs";
options = [ "subvol=boot" ];
};
*/
fileSystems."/boot" =
{ device = "/dev/disk/by-uuid/63f25199-ee0b-4991-8861-c3ba3b464ef2";
fsType = "btrfs";
options = [ "subvol=boot" ];
};
*/
fileSystems."/boot" = {
device = "/dev/disk/by-uuid/2aad8cab-7b97-47de-8608-fe9f12e211a4";
fsType = "ext4";
};
fileSystems."/boot" =
{ device = "/dev/disk/by-uuid/2aad8cab-7b97-47de-8608-fe9f12e211a4";
fsType = "ext4";
};
fileSystems."/boot/EFI" =
{ device = "/dev/disk/by-uuid/C268-79C8";
fsType = "vfat";
};
fileSystems."/boot/EFI" = {
device = "/dev/disk/by-uuid/C268-79C8";
fsType = "vfat";
};
swapDevices = [ ];

View File

@@ -2,9 +2,7 @@
{
home-manager.users.shelvacu = {
# these make vscode-remote work
imports = [
inputs.vscode-server.homeModules.default
];
imports = [ inputs.vscode-server.homeModules.default ];
services.vscode-server.enable = true;
home.stateVersion = "23.11";

View File

@@ -1,8 +1,10 @@
{ inputs, ... }: let
{ inputs, ... }:
let
padtype-pkg = inputs.padtype.packages."x86_64-linux".default;
in {
in
{
environment.systemPackages = [ padtype-pkg ];
systemd.services."padtype" = {
wantedBy = [ "multi-user.target" ];
script = "${padtype-pkg}/bin/padtype";

View File

@@ -14,20 +14,29 @@
subvolumes = {
"/root" = {
mountpoint = "/";
mountOptions = [ "compress=zstd" "noatime" ];
mountOptions = [
"compress=zstd"
"noatime"
];
};
"/home" = {
mountpoint = "/home";
mountOptions = [ "compress=zstd" "noatime" ];
mountOptions = [
"compress=zstd"
"noatime"
];
};
"/nix" = {
mountpoint = "/nix";
mountOptions = [ "compress=zstd" "noatime" ];
mountOptions = [
"compress=zstd"
"noatime"
];
};
# "/swap" = {
# mountpoint = "/.swapvol";
# swap.swapfile.size = "20M";
# };
# "/swap" = {
# mountpoint = "/.swapvol";
# swap.swapfile.size = "20M";
# };
};
};
};

104
coopdx.nix Normal file
View File

@@ -0,0 +1,104 @@
{
callPackage,
fetchFromGitHub,
autoPatchelfHook,
zlib,
curl,
libcxx,
stdenvNoCC,
nixpkgs ? <nixpkgs>,
writeTextFile,
lib,
bash,
enableTextureFix ? true,
enableDiscord ? false,
}:
let
libc_hack = writeTextFile {
name = "libc-hack";
# https://stackoverflow.com/questions/21768542/libc-h-no-such-file-or-directory-when-compiling-nanomsg-pipeline-sample
text = ''
#include <unistd.h>
#include <string.h>
#include <pthread.h>
'';
destination = "/include/libc.h";
};
target = stdenvNoCC.targetPlatform;
bits =
if target.is64bit then
"64"
else if target.is32bit then
"32"
else
throw "unspported bits";
pname = "sm64coopdx";
version = "1.0.3";
region = "us"; # dx removed support for other regions
in
(callPackage "${nixpkgs}/pkgs/games/sm64ex/generic.nix" {
inherit pname version region;
src = fetchFromGitHub {
owner = "coop-deluxe";
repo = pname;
rev = "v${version}";
hash = "sha256-cIH3escLFMcHgtFxeSKIo5nZXvaknti+EVt72uB4XXc=";
};
extraNativeBuildInputs = [ autoPatchelfHook ];
extraBuildInputs = [
zlib
curl
libcxx
libc_hack
];
# Normally there's no need to set TARGET_ARCH, but if we don't it adds -march=native which is impure
compileFlags = [
"BREW_PREFIX=/not-exist"
"TARGET_ARCH=generic"
"TARGET_BITS=${bits}"
"DISCORD_SDK=${if enableDiscord then "1" else "0"}"
"TEXTURE_FIX=${if enableTextureFix then "1" else "0"}"
];
extraMeta = {
mainProgram = pname;
homepage = "https://sm64coopdx.com/";
description = "Super Mario 64 online co-op mod, forked from sm64ex";
};
}).overrideAttrs
{
installPhase =
let
sharedLib = target.extensions.sharedLibrary;
in
''
runHook preInstall
local built=$PWD/build/${region}_pc
share=$out/share/${pname}
mkdir -p $share
cp $built/${pname} $share/${pname}-unwrapped
cp -r $built/{dynos,lang,mods,palettes} $share
cp ./baserom.*.z64 $share
${lib.optionalString enableDiscord ''
cp $built/libdiscord_game_sdk${sharedLib} $share
''}
mkdir -p $out/bin
(
echo '#!${bash}/bin/bash'
echo "cd $out/share/${pname}"
echo 'exec ./${pname}-unwrapped "$@"'
) > $out/bin/${pname}
chmod a+x $out/bin/${pname}
runHook postInstall
'';
}

106
coopdx2.nix Normal file
View File

@@ -0,0 +1,106 @@
{
# callPackage,
fetchFromGitHub,
autoPatchelfHook,
zlib,
curl,
SDL2,
hexdump,
stdenv,
writeTextFile,
lib,
bash,
python3,
sm64baserom,
enableTextureFix ? true,
enableDiscord ? false,
enableCoopNet ? true,
}:
let
libc_hack = writeTextFile {
name = "libc-hack";
# https://stackoverflow.com/questions/21768542/libc-h-no-such-file-or-directory-when-compiling-nanomsg-pipeline-sample
text = ''
#include <unistd.h>
#include <string.h>
#include <pthread.h>
'';
destination = "/include/libc.h";
};
target = stdenv.targetPlatform;
bits =
if target.is64bit then
"64"
else if target.is32bit then
"32"
else
throw "unspported bits";
pname = "sm64coopdx";
version = "1.0.3";
in
stdenv.mkDerivation {
inherit pname version;
src = fetchFromGitHub {
owner = "coop-deluxe";
repo = pname;
rev = "v${version}";
hash = "sha256-cIH3escLFMcHgtFxeSKIo5nZXvaknti+EVt72uB4XXc=";
};
buildInputs = [
python3
zlib
curl
libc_hack
SDL2
hexdump
];
enableParallelBuilding = true;
# Normally there's no need to set TARGET_ARCH, but if we don't it adds -march=native which is impure
makeFlags = [
"BREW_PREFIX=/not-exist"
"DISCORD_SDK=${if enableDiscord then "1" else "0"}"
"TEXTURE_FIX=${if enableTextureFix then "1" else "0"}"
"COOPNET=${if enableCoopNet then "1" else "0"}"
];
preBuild = ''
ln -s ${sm64baserom} baserom.us.z64
substituteInPlace Makefile \
--replace-fail ' -march=$(TARGET_ARCH) ' ' '
# workaround a bug in the build
# see https://github.com/coop-deluxe/sm64coopdx/issues/186#issuecomment-2216163935
# this can likely be removed when the next version releases
make build/us_pc/sound/sequences.bin
'';
installPhase = ''
runHook preInstall
local built=$PWD/build/us_pc
share=$out/share/${pname}
mkdir -p $share
cp $built/${pname} $share/${pname}-unwrapped
cp -r $built/{dynos,lang,mods,palettes} $share
ln -s ${sm64baserom} $share/baserom.us.z64
${lib.optionalString enableDiscord ''
cp $built/libdiscord_game_sdk* $share
''}
mkdir -p $out/bin
(
echo '#!${bash}/bin/bash'
echo "cd $out/share/${pname}"
echo 'exec ./${pname}-unwrapped "$@"'
) > $out/bin/${pname}
chmod a+x $out/bin/${pname}
runHook postInstall
'';
}

2
dcd
View File

@@ -1,3 +1,3 @@
#!/bin/sh
git add . && nixos-rebuild --flake .#compute-deck --build-host trip --target-host shelvacu@compute-deck --use-remote-sudo $@
git add . && nixos-rebuild --flake .#compute-deck --build-host trip --target-host shelvacu@compute-deck --use-remote-sudo "$@"

View File

@@ -1,4 +1,7 @@
{ nixpkgs ? import <nixpkgs> }: let
{
nixpkgs ? import <nixpkgs>,
}:
let
pkgs = nixpkgs;
lib = nixpkgs.lib;
defaultCertTemplate = {
@@ -6,50 +9,85 @@
activation_date = "1970-01-01 00:00:00 UTC";
expiration_date = "2500-01-01 00:00:00 UTC";
};
keyValToConfigLines = (key: value:
if (builtins.isString value) || (builtins.isPath value) then "${key} = \"${value}\"" else
if builtins.isInt value then "${key} = ${builtins.toString value}" else
if builtins.isList value then map (innerValue: keyValToConfigLines key innerValue) else
if builtins.isBool value then (if value then "${key}" else "# no ${key}") else
throw "don't know how to handle ${builtins.typeOf value}"
keyValToConfigLines = (
key: value:
if (builtins.isString value) || (builtins.isPath value) then
"${key} = \"${value}\""
else if builtins.isInt value then
"${key} = ${builtins.toString value}"
else if builtins.isList value then
map (innerValue: keyValToConfigLines key innerValue)
else if builtins.isBool value then
(if value then "${key}" else "# no ${key}")
else
throw "don't know how to handle ${builtins.typeOf value}"
);
mkTemplateConfig = config: lib.concatStringsSep "\n" (lib.lists.flatten (lib.attrsets.mapAttrsToList keyValToConfigLines config));
mkTemplateConfig =
config:
lib.concatStringsSep "\n" (
lib.lists.flatten (lib.attrsets.mapAttrsToList keyValToConfigLines config)
);
certCfg = pkgs.writeText "deterministic-cert.cfg" ''
serial = 1
activation_date = "1970-01-01 00:00:00 UTC"
expiration_date = "2500-01-01 00:00:00 UTC"
'';
privKeyFile = name: let
keySizeBits = 256;
keySizeHex = builtins.toString (keySizeBits / 4);
in pkgs.runCommand "deterministic-privkey-${name}.pem" {} ''
seed=$(echo ${lib.escapeShellArg (builtins.toJSON name)} | ${pkgs.ruby_3_2}/bin/ruby -rjson -e 'name = JSON.parse(STDIN.gets); print name.unpack("H*")[0].ljust(${keySizeHex}, "0")')
${pkgs.gnutls}/bin/certtool --generate-privkey --outfile=$out --key-type=rsa --sec-param=high --seed=$seed
'';
generateCert = { name, config, args, preCommands ? "" }: let
deriv = pkgs.runCommand "deterministic-cert-${name}" {} ''
mkdir -p $out
cd $out
ln -s ${privKeyFile name} privkey.pem
ln -s ${pkgs.writeText "${name}-template.cfg" (mkTemplateConfig (defaultCertTemplate // config))} template.cfg
${preCommands}
${pkgs.gnutls}/bin/certtool ${lib.escapeShellArgs args} --load-privkey=privkey.pem --outfile=cert.pem --template=template.cfg
privKeyFile =
name:
let
keySizeBits = 256;
keySizeHex = builtins.toString (keySizeBits / 4);
in
pkgs.runCommand "deterministic-privkey-${name}.pem" { } ''
seed=$(echo ${lib.escapeShellArg (builtins.toJSON name)} | ${pkgs.ruby_3_2}/bin/ruby -rjson -e 'name = JSON.parse(STDIN.gets); print name.unpack("H*")[0].ljust(${keySizeHex}, "0")')
${pkgs.gnutls}/bin/certtool --generate-privkey --outfile=$out --key-type=rsa --sec-param=high --seed=$seed
'';
in deriv // { privateKeyPath = "${deriv}/privkey.pem"; certificatePath = "${deriv}/cert.pem"; };
in {
generateCert =
{
name,
config,
args,
preCommands ? "",
}:
let
deriv = pkgs.runCommand "deterministic-cert-${name}" { } ''
mkdir -p $out
cd $out
ln -s ${privKeyFile name} privkey.pem
ln -s ${
pkgs.writeText "${name}-template.cfg" (mkTemplateConfig (defaultCertTemplate // config))
} template.cfg
${preCommands}
${pkgs.gnutls}/bin/certtool ${lib.escapeShellArgs args} --load-privkey=privkey.pem --outfile=cert.pem --template=template.cfg
'';
in
deriv
// {
privateKeyPath = "${deriv}/privkey.pem";
certificatePath = "${deriv}/cert.pem";
};
in
{
inherit privKeyFile;
selfSigned = name: config: generateCert { inherit name config; args = [ "--generate-self-signed" ]; };
caSigned = name: ca: config: generateCert {
inherit name config;
preCommands = ''
ln -s ${ca.privateKeyPath} ca-privkey.pem
ln -s ${ca.certificatePath} ca-cert.pem
'';
args = [
"--generate-certificate"
"--load-ca-certificate=ca-cert.pem"
"--load-ca-privkey=ca-privkey.pem"
];
};
selfSigned =
name: config:
generateCert {
inherit name config;
args = [ "--generate-self-signed" ];
};
caSigned =
name: ca: config:
generateCert {
inherit name config;
preCommands = ''
ln -s ${ca.privateKeyPath} ca-privkey.pem
ln -s ${ca.certificatePath} ca-cert.pem
'';
args = [
"--generate-certificate"
"--load-ca-certificate=ca-cert.pem"
"--load-ca-privkey=ca-privkey.pem"
];
};
}

View File

@@ -1,57 +0,0 @@
{ config, pkgs, lib, inputs, modulesPath, ... }:
{
imports = [
inputs.home-manager.nixosModules.default
../common/nixos.nix
(modulesPath + "/profiles/qemu-guest.nix")
];
boot.initrd.availableKernelModules = [ "virtio_pci" "usbhid" "virtio_blk" "9pnet_virtio" "9p" "autofs4" ];
boot.initrd.kernelModules = [ ];
boot.kernelModules = [ "kvm-intel" "9pnet_virtio" "9p" "autofs4" ];
boot.extraModulePackages = [ ];
system.nixos.tags = [ "host-${config.networking.hostName}" ];
networking.hostName = "devver";
boot.loader.external.enable = true;
boot.loader.external.installHook = pkgs.writeShellScript "vacuDirectBootInstaller" ''
PATH="$PATH:${pkgs.coreutils}/bin:${pkgs.gnused}/bin"
set -xev
mkdir -p /boot
cp $1/kernel /boot/kernel
cp $1/initrd /boot/initrd
cp $1/kernel-params /boot/kernel-params
sed -i "1 s|$| init=$1/sw/bin/init|" /boot/kernel-params
'';
users.users.root.shell = pkgs.bashInteractive;
fileSystems."/boot" = {
fsType = "9p";
device = "boot";
options = [
"trans=virtio"
"access=any"
"version=9p2000.L"
"posixacl"
"cache=mmap"
"nofail"
"noauto"
];
};
fileSystems."/" = {
device = "/dev/disk/by-uuid/a373835d-b942-4232-85fe-922cb1880af3";
fsType = "ext4";
};
#boot.binfmt.emulatedSystems = [ "aarch64-linux" ];
services.openssh.enable = true;
vacu.packages.nix-inspect.enable = false; #its broken for some reason I don't understand
system.stateVersion = "23.11";
}

2
dliam
View File

@@ -1,3 +1,3 @@
#!/bin/sh
git add . && nixos-rebuild --flake .#liam --build-host trip --target-host shelvacu@liam --use-remote-sudo $@
git add . && nixos-rebuild --flake .#liam --build-host trip --target-host shelvacu@liam --use-remote-sudo "$@"

3
dmmm Executable file
View File

@@ -0,0 +1,3 @@
#!/bin/sh
git add . && nixos-rebuild --flake .#mmm --build-host trip --target-host mmm --use-remote-sudo "$@"

2
dtrip
View File

@@ -1,3 +1,3 @@
#!/bin/sh
git add . && nixos-rebuild --flake .#triple-dezert --build-host trip --target-host trip --use-remote-sudo $@
git add . && nixos-rebuild --flake .#triple-dezert --build-host trip --target-host trip --use-remote-sudo "$@"

940
flake.lock generated

File diff suppressed because it is too large Load Diff

523
flake.nix
View File

@@ -3,7 +3,20 @@
inputs = {
nixpkgs.url = "nixpkgs/nixos-24.05-small";
nixpkgs-unstable.url = "nixpkgs/nixos-unstable";
# nixpkgs.url = "github:nixos/nixpkgs/be0ec1a45fe1a6f6534c451b935724ab48405f26";
nixpkgs-unstable.url = "nixpkgs/nixos-unstable-small";
flake-utils.url = "github:numtide/flake-utils";
nixvim = {
url = "github:nix-community/nixvim/nixos-24.05";
inputs.nixpkgs.follows = "nixpkgs";
inputs.home-manager.follows = "home-manager";
};
nixvim-unstable = {
url = "github:nix-community/nixvim";
inputs.nixpkgs.follows = "nixpkgs-unstable";
inputs.home-manager.follows = "home-manager-unstable";
};
nix-inspect = {
url = "github:bluskript/nix-inspect";
inputs.nixpkgs.follows = "nixpkgs";
@@ -15,16 +28,20 @@
vscode-server-unstable = {
url = "github:nix-community/nixos-vscode-server";
inputs.nixpkgs.follows = "nixpkgs-unstable";
inputs.flake-utils.follows = "flake-utils";
};
vscode-server = {
url = "github:nix-community/nixos-vscode-server";
inputs.nixpkgs.follows = "nixpkgs";
inputs.flake-utils.follows = "flake-utils";
};
nix-on-droid = {
url = "github:nix-community/nix-on-droid";
inputs.nixpkgs.follows = "nixpkgs";
inputs.home-manager.follows = "home-manager";
};
jovian-unstable = { # there is no stable jovian :cry:
jovian-unstable = {
# there is no stable jovian :cry:
url = "github:Jovian-Experiments/Jovian-NixOS";
inputs.nixpkgs.follows = "nixpkgs-unstable";
};
@@ -43,10 +60,12 @@
nix-search-cli-unstable = {
url = "github:peterldowns/nix-search-cli";
inputs.nixpkgs.follows = "nixpkgs-unstable";
inputs.flake-utils.follows = "flake-utils";
};
nix-search-cli = {
url = "github:peterldowns/nix-search-cli";
inputs.nixpkgs.follows = "nixpkgs";
inputs.flake-utils.follows = "flake-utils";
};
padtype-unstable = {
url = "gitlab:shelvacu/padtype";
@@ -56,161 +75,373 @@
url = "github:Mic92/sops-nix";
inputs.nixpkgs.follows = "nixpkgs";
};
microvm = {
url = "github:astro/microvm.nix";
inputs.nixpkgs.follows = "nixpkgs";
};
nixos-hardware.url = "github:nixos/nixos-hardware";
most-winningest = {
url = "github:captain-jean-luc/most-winningest";
inputs.nixpkgs.follows = "nixpkgs";
inputs.flake-utils.follows = "flake-utils";
};
nixos-apple-silicon-unstable = {
url = "github:tpwrules/nixos-apple-silicon";
inputs.nixpkgs.follows = "nixpkgs-unstable";
};
sm64baserom.url = "git+https://git.uninsane.org/shelvacu/sm64baserom.git";
dns = {
url = "github:nix-community/dns.nix";
inputs.nixpkgs.follows = "nixpkgs";
inputs.flake-utils.follows = "flake-utils";
};
lix-module = {
url = "git+https://git.lix.systems/lix-project/nixos-module.git?ref=stable";
inputs.nixpkgs.follows = "nixpkgs";
};
lix-module-unstable = {
url = "git+https://git.lix.systems/lix-project/nixos-module.git?ref=stable";
inputs.nixpkgs.follows = "nixpkgs-unstable";
};
};
outputs = { self, nixpkgs, nix-on-droid, home-manager, ... }@inputs: let
defaultInputs = { inherit (inputs) self nix-search-cli nix-inspect; };
defaultArgs = { inputs = defaultInputs; };
in {
debug.isoDeriv = (import "${inputs.nixpkgs}/nixos/release-small.nix" { nixpkgs = ({ revCount = 0; } // inputs.nixpkgs); });
nixosConfigurations.triple-dezert = nixpkgs.lib.nixosSystem {
system = "x86_64-linux";
modules = [ ./triple-dezert ];
specialArgs = { inputs = defaultInputs // { inherit (inputs) most-winningest; }; };
};
nixosConfigurations.compute-deck = inputs.nixpkgs-unstable.lib.nixosSystem {
system = "x86_64-linux";
modules = [ ./compute-deck ];
specialArgs = { inputs = {
jovian = inputs.jovian-unstable;
home-manager = inputs.home-manager-unstable;
vscode-server = inputs.vscode-server-unstable;
disko = inputs.disko-unstable;
padtype = inputs.padtype-unstable;
nix-search-cli = inputs.nix-search-cli-unstable;
nix-inspect = inputs.nix-inspect-unstable;
self = inputs.self;
}; };
};
nixosConfigurations.liam = nixpkgs.lib.nixosSystem {
system = "x86_64-linux";
modules = [ ./liam ];
specialArgs = { inputs = defaultInputs // { inherit (inputs) sops-nix; }; };
};
nixosConfigurations.lp0 = nixpkgs.lib.nixosSystem {
system = "x86_64-linux";
modules = [ ./lp0 ];
specialArgs = defaultArgs;
};
nixosConfigurations.shel-installer = nixpkgs.lib.nixosSystem {
system = "x86_64-linux";
modules = [ ./installer.nix ];
specialArgs = defaultArgs;
};
nixosConfigurations.devver = nixpkgs.lib.nixosSystem {
system = "x86_64-linux";
modules = [ ./devver ];
specialArgs = { inputs = defaultInputs // { inherit (inputs) home-manager; }; };
};
nixosConfigurations.fw = nixpkgs.lib.nixosSystem {
system = "x86_64-linux";
modules = [ ./fw ];
specialArgs = { inputs = defaultInputs // { inherit (inputs) nixos-hardware; }; };
};
nixOnDroidConfigurations.default = nix-on-droid.lib.nixOnDroidConfiguration {
modules = [ ./nix-on-droid ];
extraSpecialArgs = defaultArgs;
pkgs = import nixpkgs { system = "aarch64-linux"; };
};
homeConfigurations."nix-on-droid" = home-manager.lib.homeManagerConfiguration {
modules = [
./home/nix-on-droid.nix
{ _module.args.inputs = defaultInputs; }
];
pkgs = import nixpkgs { system = "aarch64-linux"; };
};
checks = nixpkgs.lib.genAttrs [ "x86_64-linux" ] (system:
let
pkgs = nixpkgs.legacyPackages.${system};
config = {
node.pkgs = pkgs;
node.pkgsReadOnly = false;
node.specialArgs.selfPackages = self.packages.${system};
#node.specialArgs.inputs = defaultInputs;
outputs =
{
self,
nixpkgs,
nix-on-droid,
...
}@inputs:
let
x86 = "x86_64-linux";
arm = "aarch64-linux";
lib = import "${nixpkgs}/lib";
mkPlain = pkgs: lib.evalModules {
modules = [
./common
{ vacu.systemKind = "server"; }
];
specialArgs = {
inherit pkgs;
inherit lib;
inherit (inputs) dns;
vacuModuleType = "plain";
inherit inputs;
};
};
mkPkgs =
arg:
let
argAttr = if builtins.isString arg then { system = arg; } else arg;
config = {
allowUnfree = true;
} // (argAttr.config or { });
in
import nixpkgs (argAttr // { inherit config; });
pkgs = mkPkgs x86;
defaultInputs = [
"nix-search-cli"
"nix-inspect"
"nixvim"
"lix-module"
];
mkNixosConfig =
{
unstable ? false,
module,
system ? "x86_64-linux",
inp ? [ ],
}@args:
let
suffix = if unstable then "-unstable" else "";
nixpkgs = inputs.${"nixpkgs" + suffix};
inp' = inp ++ defaultInputs;
thisInputs = builtins.listToAttrs (map (name: lib.nameValuePair name inputs.${name + suffix}) inp');
in
nixpkgs.lib.nixosSystem {
specialArgs = {
inputs = thisInputs // {
inherit (inputs) self;
};
inherit (inputs) dns;
vacuModuleType = "nixos";
};
inherit system;
modules = [
./common
module
];
};
in
{
debug.isoDeriv = (
import "${inputs.nixpkgs}/nixos/release-small.nix" {
nixpkgs = ({ revCount = 0; } // inputs.nixpkgs);
}
);
# overlays.requireFileSub = (
# curr: prev: { requireFile = { ... }@args: (prev args).overrideAttrs { allowSubstitutes = true; }; }
# );
# overlays.default = self.overlays.requireFileSub;
nixosConfigurations = {
triple-dezert = mkNixosConfig {
module = ./triple-dezert;
inp = [ "most-winningest" ];
};
compute-deck = mkNixosConfig {
module = ./compute-deck;
inp = [
"jovian"
"home-manager"
"vscode-server"
"disko"
"padtype"
];
unstable = true;
};
liam = mkNixosConfig {
module = ./liam;
inp = [ "sops-nix" ];
};
lp0 = mkNixosConfig { module = ./lp0; };
shel-installer = mkNixosConfig { module = ./installer.nix; };
fw = mkNixosConfig {
module = ./fw;
inp = [ "nixos-hardware" ];
};
legtop = mkNixosConfig {
module = ./legtop;
inp = [ "nixos-hardware" ];
};
mmm = mkNixosConfig {
module = ./mmm;
inp = [ "nixos-apple-silicon" ];
system = "aarch64-linux";
unstable = true;
};
};
nixOnDroidConfigurations.default = nix-on-droid.lib.nixOnDroidConfiguration {
modules = [
./common
./nix-on-droid
];
extraSpecialArgs = {
inputs = {
inherit (inputs)
nixpkgs
self
nixvim
nix-search-cli
nix-inspect
;
};
inherit (inputs) dns;
vacuModuleType = "nix-on-droid";
};
pkgs = mkPkgs {
system = arm;
overlays = [ inputs.lix-module.overlays.default ];
};
};
checks = nixpkgs.lib.genAttrs [ x86 ] (
system:
let
pkgs = mkPkgs system;
plain = mkPlain pkgs;
config = {
node.pkgs = pkgs;
node.pkgsReadOnly = false;
node.specialArgs.selfPackages = self.packages.${system};
node.specialArgs.vacuModuleType = "nixos";
};
in
{
units = plain.config.vacu.units.check;
liam = nixpkgs.lib.nixos.runTest {
hostPkgs = pkgs;
imports = [
config
./tests/liam.nix
{ node.specialArgs.inputs = self.nixosConfigurations.liam._module.specialArgs.inputs; }
];
};
trip = nixpkgs.lib.nixos.runTest {
hostPkgs = pkgs;
imports = [
config
./tests/triple-dezert.nix
{ node.specialArgs.inputs = self.nixosConfigurations.triple-dezert._module.specialArgs.inputs; }
];
};
}
);
qb = # qb is "quick build"
let
toplevelOf = name: self.nixosConfigurations.${name}.config.system.build.toplevel;
deterministicCerts = import ./deterministic-certs.nix { nixpkgs = mkPkgs x86; };
renamedAarchPackages = lib.mapAttrs' (
name: value: lib.nameValuePair (name + "-aarch64") value
) self.packages.aarch64-linux;
packages = self.packages.x86_64-linux // renamedAarchPackages;
in
rec {
fw = toplevelOf "fw";
triple-dezert = toplevelOf "triple-dezert";
trip = triple-dezert;
compute-deck = toplevelOf "compute-deck";
cd = compute-deck;
liam = toplevelOf "liam";
lp0 = toplevelOf "lp0";
legtop = toplevelOf "legtop";
lt = legtop;
mmm = toplevelOf "mmm";
shel-installer = toplevelOf "shel-installer";
iso = self.nixosConfigurations.shel-installer.config.system.build.isoImage;
check-triple-dezert = self.checks.x86_64-linux.trip.driver;
check-trip = check-triple-dezert;
check-liam = self.checks.x86_64-linux.liam.driver;
nix-on-droid = self.nixOnDroidConfigurations.default.activationPackage;
nod = nix-on-droid;
nod-bootstrap-x86_64 = inputs.nix-on-droid.packages.x86_64-linux.bootstrapZip-x86_64;
nod-bootstrap-aarch64 = inputs.nix-on-droid.packages.x86_64-linux.bootstrapZip-aarch64;
dc-priv = deterministicCerts.privKeyFile "test";
dc-cert = deterministicCerts.selfSigned "test" { };
sm64 = packages.sm64coopdx;
ak = packages.authorizedKeys;
my-sops = packages.wrappedSops;
inherit (inputs.nixos-apple-silicon-unstable.packages.aarch64-linux)
m1n1
uboot-asahi
installer-bootstrap
;
installer-bootstrap-cross =
inputs.nixos-apple-silicon-unstable.packages.x86_64-linux.installer-bootstrap;
}
// packages;
brokenBuilds = [
"sm64coopdx-aarch64"
"installer-bootstrap"
];
all =
let
linksNoContext = removeAttrs self.qb self.brokenBuilds;
links = builtins.mapAttrs (
name: val: builtins.addErrorContext "while evaluating link ${name}" val
) linksNoContext;
in
pkgs.runCommand "nix-stuff-all"
{
__structuredAttrs = true;
inherit links;
}
''
mkdir $out
cd $out
eval "$(${pkgs.jq}/bin/jq '.links | to_entries | map("ln -s "+.value+" "+.key) | join("\n")' /build/.attrs.json -r)"
'';
allPure = self.all.overrideAttrs (prev: {
links = removeAttrs prev.links [
"nix-on-droid"
"nod"
"nod-bootstrap-x86_64"
"nod-bootstrap-aarch64"
];
});
archive =
let
# We don't want iso/img derivations here because they de-dupe terribly. Any change anywhere requires generating a new iso/img file.
allButImgs = self.all.overrideAttrs (prev: {
links = removeAttrs prev.links [ "iso" ];
});
isoContents = lib.concatStringsSep "\n" (
map (
c: "${c.source} => ${c.target}"
) self.nixosConfigurations.shel-installer.config.isoImage.contents
);
isoContentsPkg = pkgs.writeText "iso-contents" isoContents;
info = pkgs.closureInfo { rootPaths = [ allButImgs.drvPath ]; };
in
allButImgs.overrideAttrs (prev: {
links = prev.links // {
iso-contents = isoContentsPkg;
build-deps = info;
};
});
}
// (inputs.flake-utils.lib.eachDefaultSystem (
system:
let
pkgs = import inputs.nixpkgs-unstable {
inherit system;
config.allowUnfree = true;
overlays = [ inputs.sm64baserom.overlays.default ];
};
_plain = mkPlain pkgs;
inherit (_plain.config.vacu) withAsserts;
plain = _plain.config.vacu.withAsserts _plain;
# dnsModule = lib.evalModules {
# modules = [
# {
# config._module.check = false;
# options.vacu.dns = lib.mkOption {
# default = { };
# type = lib.types.attrsOf inputs.dns.lib.types.zone;
# };
# }
# ];
# };
in
{
liam = nixpkgs.lib.nixos.runTest {
hostPkgs = pkgs;
imports = [ config ./tests/liam.nix { node.specialArgs.inputs = self.nixosConfigurations.liam._module.specialArgs.inputs; } ];
formatter = pkgs.nixfmt-rfc-style;
apps.sops = {
type = "app";
program = lib.getExe self.packages.${system}.wrappedSops;
};
trip = nixpkgs.lib.nixos.runTest {
hostPkgs = pkgs;
imports = [ config ./tests/triple-dezert.nix { node.specialArgs.inputs = self.nixosConfigurations.triple-dezert._module.specialArgs.inputs; } ];
vacuconfig = plain.config;
packages = rec {
nix-inspect = inputs.nix-inspect.packages.${system}.default;
nix-search-cli = inputs.nix-search-cli.packages.${system}.default;
units = plain.config.vacu.units.finalPackage;
sourceTree = plain.config.vacu.sourceTree;
z3 = pkgs.callPackage ./packages/z3 { };
bandcamp-collection-downloader = pkgs.callPackage ./packages/bcd { };
bcd = bandcamp-collection-downloader;
sm64coopdx = pkgs.callPackage ./coopdx2.nix { };
# snmpb = pkgs.libsForQt5.callPackage ./packages/snmpb/package.nix { };
# snmp-mibs-downloader = pkgs.callPackage ./packages/snmp-mibs-downloader.nix { };
authorizedKeys = pkgs.writeText "authorizedKeys" (
lib.concatStringsSep "\n" (
lib.mapAttrsToList (k: v: "${v} ${k}") (withAsserts plain.config.vacu.ssh.authorizedKeys)
)
);
update-git-keys = withAsserts pkgs.callPackage ./scripts/update-git-keys.nix {
inherit (plain) config;
};
sopsConfig = withAsserts plain.config.vacu.sopsConfig;
wrappedSops = withAsserts plain.config.vacu.wrappedSops;
dns = withAsserts import ./scripts/dns {
inherit pkgs lib inputs;
inherit (plain) config;
};
# dnsOptions = (pkgs.nixosOptionsDoc { options = dnsModule.options; }).optionsCommonMark;
vnopnCA = pkgs.writeText "vnopnCA.cert" plain.config.vacu.vnopnCA;
nixvim = inputs.nixvim.legacyPackages.${system}.makeNixvimWithModule {
extraSpecialArgs = {
inputs = { };
};
module = {
imports = [ ./nixvim ];
};
};
};
}
);
nixosModules.common = import ./common/module.nix;
packages.x86_64-linux.snmpb = nixpkgs.legacyPackages.x86_64-linux.libsForQt5.callPackage ./packages/snmpb/package.nix {};
packages.x86_64-linux.snmp-mibs-downloader = nixpkgs.legacyPackages.x86_64-linux.callPackage ./packages/snmp-mibs-downloader.nix {};
packages.x86_64-linux.digitalOceanImage = import ./generic-digitalocean-nixos.nix { inherit inputs; };
packages.x86_64-linux.authorizedKeys = let
pkgs = nixpkgs.legacyPackages.x86_64-linux;
in pkgs.writeText "authorizedKeys" (pkgs.lib.concatStringsSep "\n" self.nixosConfigurations.fw.config.vacu.ssh.authorizedKeys);
packages.aarch64-linux.authorizedKeys = let
pkgs = nixpkgs.legacyPackages.aarch64-linux;
in pkgs.writeText "authorizedKeys" (pkgs.lib.concatStringsSep "\n" self.nixOnDroidConfigurations.default.config.vacu.ssh.authorizedKeys);
qb = /* qb is "quick build" */ let
toplevelOf = name: self.nixosConfigurations.${name}.config.system.build.toplevel;
deterministicCerts = import ./deterministic-certs.nix { nixpkgs = inputs.nixpkgs.legacyPackages.x86_64-linux; };
pkgs = nixpkgs.legacyPackages.x86_64-linux;
in rec {
# nix-on-droid is impure >:(
# nod = self.nixOnDroidConfigurations.default.activationPackage;
fw = toplevelOf "fw";
triple-dezert = toplevelOf "triple-dezert";
trip = triple-dezert;
compute-deck = toplevelOf "compute-deck";
cd = compute-deck;
liam = toplevelOf "liam";
lp0 = toplevelOf "lp0";
devver = toplevelOf "devver";
shel-installer = toplevelOf "shel-installer";
iso = self.nixosConfigurations.shel-installer.config.system.build.isoImage;
do = self.packages.x86_64-linux.digitalOceanImage;
snmpb = self.packages.x86_64-linux.snmpb;
check-triple-dezert = self.checks.x86_64-linux.trip.driver;
check-trip = check-triple-dezert;
check-liam = self.checks.x86_64-linux.liam.driver;
authorizedKeys = self.packages.x86_64-linux.authorizedKeys;
authorizedKeysAarch = self.packages.aarch64-linux.authorizedKeys;
ak = authorizedKeys;
dc-priv = deterministicCerts.privKeyFile "test";
dc-cert = deterministicCerts.selfSigned "test" {};
};
all = let
pkgs = nixpkgs.legacyPackages.x86_64-linux;
symlinkCommands = pkgs.lib.mapAttrsToList (name: pkg: "ln -s ${pkg} ${name}") self.qb;
in pkgs.runCommand "nix-stuff-all" {} ''
mkdir $out
cd $out
${pkgs.lib.concatStringsSep "\n" symlinkCommands}
'';
allWithBuildDeps = nixpkgs.legacyPackages.x86_64-linux.closureInfo { rootPaths = [ self.all.drvPath ]; };
};
));
}

View File

@@ -1,4 +1,5 @@
{ pkgs, ... }: {
{ pkgs, ... }:
{
vacu.packages = pkgs.androidStudioPackages.stable.all;
users.users.shelvacu.extraGroups = [ "kvm" ];
}

View File

@@ -1,23 +1,33 @@
# everything to interact with my apex flex, pcsc stuff, fido2 stuff, etc
{ pkgs, ... }: {
{ pkgs, config, ... }:
let
# to match package used in config.services.pcscd, unfortunately not exposed like usual
pcsclite-pkg = if config.security.polkit.enable then pkgs.pcscliteWithPolkit else pkgs.pcsclite;
in
{
# apparently this is already enabled??
# nixpkgs.overlays = [ ( final: prev: {
# libfido2 = prev.libfido2.override { withPcsclite = true; };
# } ) ];
vacu.packages = with pkgs; [
libfido2
pcsclite
pcsc-tools
scmccid
opensc
];
vacu.packages =
(with pkgs; [
libfido2
pcsc-tools
scmccid
opensc
])
++ [ pcsclite-pkg ];
services.pcscd.enable = true;
# conflicts with pcscd, see https://stackoverflow.com/questions/55144458/unable-to-claim-usb-interface-device-or-resource-busy-stuck
boot.blacklistedKernelModules = [ "pn533_usb" "pn533" "nfc" ];
boot.blacklistedKernelModules = [
"pn533_usb"
"pn533"
"nfc"
];
# bunch of stuff from https://wiki.nixos.org/wiki/Web_eID
# Tell p11-kit to load/proxy opensc-pkcs11.so, providing all available slots
# (PIN1 for authentication/decryption, PIN2 for signing).
# environment.etc."pkcs11/modules/opensc-pkcs11".text = ''

View File

@@ -1,52 +1,77 @@
{ config, inputs, pkgs, lib, ... }: {
{
inputs,
pkgs,
...
}:
{
imports = [
../common/nixos.nix
inputs.nixos-hardware.nixosModules.framework-16-7040-amd
./apex.nix
./android.nix
./thunderbolt.nix
./fwupd.nix
./zfs.nix
./virtualbox.nix
];
#boot.loader.grub.configurationLimit = 5;
system.nixos.tags = [ "host-${config.networking.hostName}" ];
vacu.hostName = "fw";
vacu.shell.color = "magenta";
vacu.verifySystem.expectedMac = "e8:65:38:52:5c:59";
vacu.systemKind = "desktop";
boot.binfmt.emulatedSystems = [ "aarch64-linux" ];
networking.networkmanager.enable = true;
# boot.kernelParams = [ "nvme.noacpi=1" ]; # DONT DO IT: breaks shit even more
services.fprintd.enable = false; #kinda broken
vacu.packages = with pkgs; [
bitwarden-desktop
nheko
librewolf
brave
thunderbird
wl-clipboard
nextcloud-client
signal-desktop
fw-ectool
framework-tool
iio-sensor-proxy
power-profiles-daemon
acpi
jellyfin-media-player
vlc
dmidecode
prismlauncher
ffmpeg_7-full
wireshark
obsidian
dino
aircrack-ng
libreoffice-qt6-fresh
# null actually means everything https://github.com/NixOS/nixpkgs/commit/5efd65b2d94b0ac0cf155e013b6747fa22bc04c3
(inkscape-with-extensions.override { inkscapeExtensions = null; })
libsmi
net-snmp
];
services.fprintd.enable = false; # kinda broken
services.fwupd.enable = true;
#fwupd gets confused by the multiple EFI partitions, I think I just have to pick one
#update: it didn't work, I dunno why. Leaving this here anyways
services.fwupd.daemonSettings.EspLocation = lib.mkForce "/boot0";
users.users.shelvacu.extraGroups = [ "dialout" ];
vacu.packages =
(with pkgs; [
bitwarden-desktop
nheko
librewolf
brave
thunderbird
wl-clipboard
nextcloud-client
signal-desktop
fw-ectool
framework-tool
iio-sensor-proxy
power-profiles-daemon
acpi
jellyfin-media-player
vlc
dmidecode
prismlauncher
ffmpeg_7-full
wireshark
obsidian
dino
aircrack-ng
libreoffice-qt6-fresh
gimp
# null actually means everything https://github.com/NixOS/nixpkgs/commit/5efd65b2d94b0ac0cf155e013b6747fa22bc04c3
(inkscape-with-extensions.override { inkscapeExtensions = null; })
libsmi
net-snmp
android-tools
ghidra
wineWowPackages.stableFull
wineWowPackages.fonts
winetricks
tremotesf
smartmontools
nvme-cli
arduino-ide
headsetcontrol
OSCAR
])
++ [ inputs.self.packages.${pkgs.system}.sm64coopdx ];
networking.firewall.enable = false;
services.xserver.enable = true;
services.displayManager.sddm.enable = true;
@@ -68,42 +93,54 @@
}
];
networking.hostName = "fw"; # Define your hostname.
networking.hostId = "c6e309d5";
boot.zfs.extraPools = [ "fw" ];
boot.kernelPackages = config.boot.zfs.package.latestCompatibleLinuxPackages;
systemd.services.zfs-mount.enable = false;
services.openssh.enable = true;
system.stateVersion = "23.11"; # Did you read the comment?
boot.initrd.availableKernelModules = [ "nvme" "xhci_pci" "thunderbolt" "usb_storage" "usbhid" "sd_mod" ];
boot.initrd.kernelModules = [ ];
boot.initrd.availableKernelModules = [
"nvme"
"xhci_pci"
"thunderbolt"
"usb_storage"
"usbhid"
"sd_mod"
];
#boot.initrd.kernelModules = [ ];
boot.kernelModules = [ "kvm-amd" ];
boot.extraModulePackages = [ ];
#boot.extraModulePackages = [ ];
fileSystems."/" =
{ device = "fw/root";
fsType = "zfs";
};
fileSystems."/" = {
device = "fw/root";
fsType = "zfs";
};
fileSystems."/boot0" =
{ device = "/dev/disk/by-label/BOOT0";
fsType = "vfat";
options = [ "fmask=0022" "dmask=0022" ];
};
fileSystems."/boot0" = {
device = "/dev/disk/by-label/BOOT0";
fsType = "vfat";
options = [
"fmask=0022"
"dmask=0022"
];
};
fileSystems."/boot1" =
{ device = "/dev/disk/by-label/BOOT1";
fsType = "vfat";
options = [ "fmask=0022" "dmask=0022" ];
};
fileSystems."/boot1" = {
device = "/dev/disk/by-label/BOOT1";
fsType = "vfat";
options = [
"fmask=0022"
"dmask=0022"
];
};
hardware.cpu.amd.updateMicrocode = true;
hardware.enableAllFirmware = true;
hardware.opengl = {
driSupport = true;
driSupport32Bit = true;
extraPackages = [ pkgs.rocmPackages.clr.icd pkgs.amdvlk ];
extraPackages = [
pkgs.rocmPackages.clr.icd
pkgs.amdvlk
];
};
programs.nix-ld.enable = true;
programs.steam = {
@@ -121,6 +158,7 @@
hardware.bluetooth.powerOnBoot = true;
services.blueman.enable = true;
services.postgresql.enable = true; #for development
}
services.postgresql.enable = true; # for development
virtualisation.waydroid.enable = true;
}

43
fw/experiment.nix Normal file
View File

@@ -0,0 +1,43 @@
{
pkgs,
config,
lib,
...
}:
let
version = "6.10.4";
hash = "sha256:1y2m2pqrvsgr9ng72nnh4yvsprkvkznhnmn4p8g78350bzyrvip2";
customKernel = pkgs.linux_6_10.override {
inherit version;
src = pkgs.fetchurl {
url = "mirror://kernel/linux/kernel/v${lib.versions.major version}.x/linux-${version}.tar.xz";
inherit hash;
};
modDirVersion = lib.versions.pad 3 version;
};
customKernelPackages = pkgs.linuxPackagesFor customKernel;
in
{
system.nixos.tags = [
"EXPERIMENT"
"kernel-${config.boot.kernelPackages.kernel.version}"
];
boot.kernelPackages = lib.mkForce customKernelPackages;
# boot.zfs.extraPools = lib.mkForce [];
# fileSystems."/".fsType = lib.mkForce "ext4";
vacu.packages.sm64coopdx.enable = false;
vacu.verifySystem.expectedMac = lib.mkForce null;
}
# good:
# Linux fw 6.6.50 #1-NixOS SMP PREEMPT_DYNAMIC Sun Sep 8 05:54:49 UTC 2024 x86_64 GNU/Linux
# Linux fw 6.8.12 #1-NixOS SMP PREEMPT_DYNAMIC Thu May 30 07:49:53 UTC 2024 x86_64 GNU/Linux
# linux-6.9.12
# 6.10.4 (maybe?? sus)
# Linux fw 6.10.10 #1-NixOS SMP PREEMPT_DYNAMIC Thu Sep 12 09:13:13 UTC 2024 x86_64 GNU/Linux (but this was supposed to be 6.10.4....)
# bad:
# Linux fw 6.10.10-gnu #1-NixOS SMP PREEMPT_DYNAMIC Tue Jan 1 00:00:00 UTC 1980 x86_64 GNU/Linux
# linux linux-6.10.10

8
fw/fwupd.nix Normal file
View File

@@ -0,0 +1,8 @@
{ config, lib, ... }:
{
vacu.packages = [ config.services.fwupd.package ];
services.fwupd.enable = true;
#fwupd gets confused by the multiple EFI partitions, I think I just have to pick one
#update: it didn't work, I dunno why. Leaving this here anyways
services.fwupd.daemonSettings.EspLocation = lib.mkForce "/boot0";
}

10
fw/thunderbolt.nix Normal file
View File

@@ -0,0 +1,10 @@
{ pkgs, config, ... }:
{
services.hardware.bolt.enable = true;
vacu.packages = [
pkgs.thunderbolt
config.services.hardware.bolt.package
pkgs.kdePackages.plasma-thunderbolt
];
}

8
fw/virtualbox.nix Normal file
View File

@@ -0,0 +1,8 @@
{ ... }:
{
virtualisation.virtualbox.host = {
enable = true;
enableExtensionPack = true;
};
users.extraGroups.vboxusers.members = [ "shelvacu" ];
}

12
fw/zfs.nix Normal file
View File

@@ -0,0 +1,12 @@
{
pkgs,
...
}:
{
boot.zfs.extraPools = [ "fw" ];
# config.boot.zfs.package.latestCompatibleLinuxPackages is fucked, if there are multiple compatible linuxes of the same version, it picks effectively an arbitrary one
boot.kernelPackages = pkgs.linuxKernel.packages.linux_6_6;
systemd.services.zfs-mount.enable = false;
# see also fileSystems."/"
}

View File

@@ -1,10 +0,0 @@
{ inputs, system ? "x86_64-linux" }:
let
pkgs = inputs.nixpkgs.legacyPackages.${system};
config = { config, ... }: {
imports = [ "${inputs.nixpkgs}/nixos/modules/virtualisation/digital-ocean-image.nix" ];
system.stateVersion = config.system.nixos.release;
};
in
(pkgs.nixos config).digitalOceanImage

View File

@@ -1,18 +1,18 @@
{ config, inputs, modulesPath, lib, ... }: {
{
config,
modulesPath,
lib,
...
}:
{
imports = [
"${modulesPath}/installer/cd-dvd/installation-cd-minimal.nix"
./common/nixos.nix
];
# this is an installer image, created anew every time. There's no state we need to worry about messing up
system.stateVersion = config.system.nixos.version;
system.stateVersion = config.system.nixos.version;
isoImage.isoBaseName = "nixos-shel-installer";
services.openssh.settings.PermitRootLogin = lib.mkForce "yes";
# boot.kernelPatches = [{
# name = "foo";
# patch = null;
# extraStructuredConfig = {
# VIRTIO = lib.kernel.yes;
# VIRTIO_BLK = lib.kernel.yes;
# };
# }];
vacu.hostName = "vacuInstaller";
vacu.shell.color = "red";
vacu.systemKind = "server";
}

7
legtop/bluetooth.nix Normal file
View File

@@ -0,0 +1,7 @@
{ ... }:
{
hardware.bluetooth.enable = true;
hardware.bluetooth.powerOnBoot = true;
services.blueman.enable = true;
}

80
legtop/default.nix Normal file
View File

@@ -0,0 +1,80 @@
{ pkgs, inputs, ... }:
{
imports = [
../common/nixos.nix
inputs.nixos-hardware.nixosModules.gpd-micropc
./hardware.nix
./bluetooth.nix
];
vacu.hostName = "legtop";
vacu.shortHostName = "lt";
vacu.shell.color = "blue";
vacu.verifySystem.expectedMac = "30:9e:90:33:01:07";
vacu.systemKind = "desktop";
system.stateVersion = "24.05";
boot.binfmt.emulatedSystems = [ "aarch64-linux" ];
networking.networkmanager.enable = true;
vacu.packages =
(with pkgs; [
bitwarden-desktop
nheko
librewolf
brave
thunderbird
wl-clipboard
nextcloud-client
signal-desktop
iio-sensor-proxy
power-profiles-daemon
acpi
jellyfin-media-player
vlc
dmidecode
prismlauncher
ffmpeg_7-full
wireshark
obsidian
dino
aircrack-ng
libreoffice-qt6-fresh
gimp
# null actually means everything https://github.com/NixOS/nixpkgs/commit/5efd65b2d94b0ac0cf155e013b6747fa22bc04c3
(inkscape-with-extensions.override { inkscapeExtensions = null; })
libsmi
net-snmp
android-tools
ghidra
wineWowPackages.stableFull
wineWowPackages.fonts
winetricks
lutris
])
++ [ inputs.self.packages.${pkgs.system}.sm64coopdx ];
services.openssh.enable = true;
services.xserver.enable = true;
services.displayManager.sddm.enable = true;
services.desktopManager.plasma6.enable = true;
boot.loader.grub.enable = true;
boot.loader.grub.efiSupport = true;
boot.loader.grub.device = "nodev";
boot.loader.efi.canTouchEfiVariables = true;
hardware.cpu.intel.updateMicrocode = true;
hardware.enableAllFirmware = true;
services.fwupd.enable = true;
services.pipewire = {
enable = true;
alsa.enable = true;
alsa.support32Bit = true;
pulse.enable = true;
};
programs.steam.enable = true;
}

32
legtop/hardware.nix Normal file
View File

@@ -0,0 +1,32 @@
{ ... }:
{
boot.initrd.availableKernelModules = [
"ahci"
"xhci_pci"
"usbhid"
"usb_storage"
"sd_mod"
"sdhci_pci"
];
boot.initrd.kernelModules = [ ];
boot.kernelModules = [ "kvm-intel" ];
boot.extraModulePackages = [ ];
fileSystems."/" = {
device = "/dev/disk/by-uuid/e3aebf24-be76-4064-a9f5-3930c8cd1382";
fsType = "ext4";
};
boot.initrd.luks.devices."root".device = "/dev/disk/by-uuid/7fd2ca2d-7faf-4d40-8cde-ce531fa679b5";
fileSystems."/boot" = {
device = "/dev/disk/by-uuid/4C47-D9A3";
fsType = "vfat";
options = [
"fmask=0022"
"dmask=0022"
];
};
nixpkgs.hostPlatform = "x86_64-linux";
hardware.cpu.intel.updateMicrocode = true;
}

View File

@@ -1,8 +1,13 @@
{ modulesPath, config, lib, ... }: {
{
modulesPath,
config,
lib,
...
}:
{
imports = [
(modulesPath + "/installer/scan/not-detected.nix")
(modulesPath + "/virtualisation/digital-ocean-config.nix")
../common/nixos.nix
./nginx.nix
./sops.nix
./dovecot.nix
@@ -12,44 +17,56 @@
./network.nix
];
options = let
mkReadOnly = val: lib.options.mkOption { default = val; readOnly = true; };
in {
vacu.liam = {
shel_domains = mkReadOnly [
"shelvacu.com"
"dis8.net"
"mail.dis8.net"
"jean-luc.org"
"in.jean-luc.org"
"vacu.store"
];
julie_domains = mkReadOnly [
"violingifts.com"
"theviolincase.com"
"shop.theviolincase.com"
];
domains = mkReadOnly (config.vacu.liam.shel_domains ++ config.vacu.liam.julie_domains);
relayhost = lib.options.mkOption {
type = lib.types.str;
# mailhop is duocircle
default = "[outbound.mailhop.org]:587 [relay.dynu.com]:587";
options =
let
mkReadOnly =
val:
lib.options.mkOption {
default = val;
readOnly = true;
};
in
{
vacu.liam = {
shel_domains = mkReadOnly [
"shelvacu.com"
"dis8.net"
"mail.dis8.net"
"jean-luc.org"
"in.jean-luc.org"
"vacu.store"
];
julie_domains = mkReadOnly [
"violingifts.com"
"theviolincase.com"
"shop.theviolincase.com"
];
domains = mkReadOnly (config.vacu.liam.shel_domains ++ config.vacu.liam.julie_domains);
relayhost = lib.options.mkOption {
type = lib.types.str;
# mailhop is duocircle
default = "[outbound.mailhop.org]:587 [relay.dynu.com]:587";
};
reservedIpLocal = mkReadOnly "10.46.0.7";
};
reservedIpLocal = mkReadOnly "10.46.0.7";
};
};
config = {
system.nixos.tags = [ "host-${config.networking.hostName}" ];
networking.hostName = "liam";
vacu.hostName = "liam";
vacu.shell.color = "cyan";
networking.domain = "dis8.net";
vacu.systemKind = "minimal";
hardware.enableAllFirmware = false;
hardware.enableRedistributableFirmware = false;
# networking.interfaces."ens3".useDHCP = false;
services.openssh.enable = true;
virtualisation.digitalOcean.setSshKeys = false;
users.users.root.openssh.authorizedKeys.keys = config.users.users.shelvacu.openssh.authorizedKeys.keys;
users.users.root.openssh.authorizedKeys.keys =
config.users.users.shelvacu.openssh.authorizedKeys.keys;
system.stateVersion = "23.11";
};

View File

@@ -1,7 +1,13 @@
{ config, pkgs, lib, ... }:
{
config,
pkgs,
lib,
...
}:
let
inherit (config.vacu.liam) domains;
in {
inherit (config.vacu.liam) domains;
in
{
services.opendkim = {
enable = true;
keyPath = "/run/secrets/dkimkeys";
@@ -15,4 +21,4 @@ in {
systemd.services.postfix.after = [ "opendkim.service" ];
}
# 2024-03-liam._domainkey
# v=DKIM1; k=rsa; s=email; p=MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAqoFR9cwOb+IpvaqrI55zlouWMUk5hjKHQARajqeOev2I6Gc3QIvU8btyhKCJu7pwxr+DxK/9HeqTmweCSXZmLlVZ6LjW80aAg+8l2DyMKZPaTowSQcExfNMwHqI1ByUPx49LQQEzvwv8Lx3To2+JghZNXHUx7gcraoCUQnRNzCMoMsGF25Yyt4piW6SXKWsbWHVXaL2i953PtT6agJYqssnBqPx6wqibrkeB9MbtSw97L5oQDaDLmJzEK54vRjFFV4X6/Q1d3D6M5PH0XGm6WEhrNEPgMAAZ6rBqi+AoXUz9E9B+kE/Zc6krCTiV0Y1uL83RCILaEJIjRsHqgrGRYEIBUb4Z5d4CgB3szixzaFTmG+XAgDLGnAHRNGeOn0bUmj35miLUopzGJgHCUQYjaaXMH4FSQMYBFPVqZ1aSiZO0EC/mbLlFbBy51RYPJQK0IusN4IqaBYw6jZYMEVlLWkNb34bfNtPKwoG4T3UjxmSRpfiNCFjYd4DaOz/FBAvUL9bx+qU7O6EZRtslROaWN18uSt20hBH0SpvEovj7vBgWWqXG/chNS7YSSaf3Tlb3I5NbqbmvwFF0t8uuEtN0Wh26qMuOKx70K90B9FpJBpfIk/w8FQ80kP6spbMN1v1T5fA7oZMV1fOn1IezH4wE5Yk/3dS+OXJ4YiLH/hWfjecCAwEAAQ==
# v=DKIM1; k=rsa; s=email; p=MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAqoFR9cwOb+IpvaqrI55zlouWMUk5hjKHQARajqeOev2I6Gc3QIvU8btyhKCJu7pwxr+DxK/9HeqTmweCSXZmLlVZ6LjW80aAg+8l2DyMKZPaTowSQcExfNMwHqI1ByUPx49LQQEzvwv8Lx3To2+JghZNXHUx7gcraoCUQnRNzCMoMsGF25Yyt4piW6SXKWsbWHVXaL2i953PtT6agJYqssnBqPx6wqibrkeB9MbtSw97L5oQDaDLmJzEK54vRjFFV4X6/Q1d3D6M5PH0XGm6WEhrNEPgMAAZ6rBqi+AoXUz9E9B+kE/Zc6krCTiV0Y1uL83RCILaEJIjRsHqgrGRYEIBUb4Z5d4CgB3szixzaFTmG+XAgDLGnAHRNGeOn0bUmj35miLUopzGJgHCUQYjaaXMH4FSQMYBFPVqZ1aSiZO0EC/mbLlFbBy51RYPJQK0IusN4IqaBYw6jZYMEVlLWkNb34bfNtPKwoG4T3UjxmSRpfiNCFjYd4DaOz/FBAvUL9bx+qU7O6EZRtslROaWN18uSt20hBH0SpvEovj7vBgWWqXG/chNS7YSSaf3Tlb3I5NbqbmvwFF0t8uuEtN0Wh26qMuOKx70K90B9FpJBpfIk/w8FQ80kP6spbMN1v1T5fA7oZMV1fOn1IezH4wE5Yk/3dS+OXJ4YiLH/hWfjecCAwEAAQ==

View File

@@ -1,4 +1,9 @@
{ config, pkgs, lib, ... }:
{
config,
pkgs,
lib,
...
}:
{
networking.firewall.allowedTCPPorts = [ 993 ];
systemd.tmpfiles.settings.whatever."/var/lib/mail".d = {
@@ -17,7 +22,11 @@
sslServerKey = config.security.acme.certs."liam.dis8.net".directory + "/key.pem";
sslServerCert = config.security.acme.certs."liam.dis8.net".directory + "/full.pem";
enablePAM = false;
protocols = lib.mkForce [ "imap" "lmtp" "sieve" ];
protocols = lib.mkForce [
"imap"
"lmtp"
"sieve"
];
modules = [ pkgs.dovecot_pigeonhole ];
mailUser = "vmail";
mailGroup = "vmail";

View File

@@ -1,10 +1,36 @@
{ config, lib, pkgs, ... }: let
inherit (config.vacu.liam) shel_domains julie_domains domains relayhost;
{
config,
lib,
pkgs,
...
}:
let
inherit (config.vacu.liam)
shel_domains
julie_domains
domains
relayhost
;
debug = false;
fqdn = config.networking.fqdn;
dovecot_transport = "lmtp:unix:private/dovecot-lmtp";
in {
networking.firewall.allowedTCPPorts = [ 25 465 ];
reject_spam_sources = [
"reject-spam-test@example.com"
"buyerservice@made-in-china.com"
"upgrade-plans@asuswebstorage.com"
"info@rfidlabel.com"
];
banned_ips = [
"210.242.134.20/26"
];
# must be bigger than gmail's 25MB "attachment limit" which after base64 encoding (x 1.33) is ~33MB
mailSizeLimit = 35 * 1024 * 1024;
in
{
networking.firewall.allowedTCPPorts = [
25
465
];
vacu.acmeCertDependencies."liam.dis8.net" = [ "postfix.service" ];
services.postfix = {
@@ -13,12 +39,15 @@ in {
# this goes into virtual_alias_maps
# "Note: for historical reasons, virtual_alias_maps apply to recipients in all domain classes, not only the virtual alias domain class."
virtual = ''
julie@shelvacu.com julie
mom@shelvacu.com julie
psv@shelvacu.com psv
'' + (lib.concatMapStringsSep "\n" (d: "@${d} shelvacu") shel_domains) + "\n"
+ (lib.concatMapStringsSep "\n" (d: "@${d} julie") julie_domains);
virtual =
''
julie@shelvacu.com julie
mom@shelvacu.com julie
psv@shelvacu.com psv
''
+ (lib.concatMapStringsSep "\n" (d: "@${d} shelvacu") shel_domains)
+ "\n"
+ (lib.concatMapStringsSep "\n" (d: "@${d} julie") julie_domains);
transport = ''
shelvacu@${fqdn} ${dovecot_transport}
@@ -33,8 +62,18 @@ in {
rootAlias = "shelvacu";
enableSubmission = false;
enableSubmissions = true;
mapFiles.header_checks = pkgs.writeText "header-checks" ("/./ INFO checker headers\n" + (lib.concatMapStringsSep "\n" (d: "/^(from|x-original-from|return-path|mail-?from):.*@${lib.escape [ "." ] d}\\s*>?\\s*$/ REJECT") domains));
mapFiles.sender_access = pkgs.writeText "sender-access" (lib.concatMapStringsSep "\n" (d: "${d} REJECT") domains);
mapFiles.header_checks = pkgs.writeText "header-checks" (
"/./ INFO checker headers\n"
+ (lib.concatMapStringsSep "\n" (
d: "/^(from|x-original-from|return-path|mail-?from):.*@${lib.escape [ "." ] d}\\s*>?\\s*$/ REJECT"
) domains)
);
mapFiles.sender_access = pkgs.writeText "sender-access" (
lib.concatMapStringsSep "\n" (pattern: "${pattern} REJECT spam") (domains ++ reject_spam_sources)
);
mapFiles.banned_ips = pkgs.writeText "banned-ips" (
lib.concatMapStringsSep "\n" (ip: "${ip} REJECT spam") banned_ips
);
# hack to get postfix to add a X-Original-To header
mapFiles.add_envelope_to = pkgs.writeText "addenvelopeto" "/(.+)/ PREPEND X-Envelope-To: $1";
mapFiles.sender_transport = pkgs.writeText "sender-transport" "@shelvacu.com relayservice";
@@ -47,12 +86,15 @@ in {
virtual_alias_domains =
${lib.concatStringsSep ",\n " domains}
message_size_limit = ${toString mailSizeLimit}
sender_dependent_default_transport_maps = hash:/etc/postfix/sender_transport
sender_dependent_relayhost_maps = hash:/etc/postfix/sender_relay
header_checks = pcre:/etc/postfix/header_checks
smtpd_sender_restrictions = check_sender_access hash:/etc/postfix/sender_access
smtpd_recipient_restrictions = check_recipient_access pcre:/etc/postfix/add_envelope_to
smtpd_sender_restrictions = check_sender_access hash:/etc/postfix/sender_access permit
smtpd_client_restrictions = check_client_access cidr:/etc/postfix/banned_ips permit
smtpd_recipient_restrictions = check_recipient_access pcre:/etc/postfix/add_envelope_to permit
recipient_delimiter = +
#we should never use these transport methods unless thru transport map
@@ -61,8 +103,8 @@ in {
# X.3.X = mail system failure
# X.3.5 = System incorrectly configured
# I would've never thought there'd be a standard way to specifically say "you found an error in my config"
local_transport = error:5.3.5 how did this even hapenn??
virtual_transport = error:5.3.5 how did this even happenn??
local_transport = error:5.3.5 how did this even happen?? (e-local)
virtual_transport = error:5.3.5 how did this even happen?? (e-virtual)
# X.7.1 = Delivery not authorized, message refused
relay_transport = error:5.7.1 relay is so very disabled
@@ -76,28 +118,36 @@ in {
# smtp_bind_address = 10.46.0.7
# inet_interfaces = all
# inet_protocols = ipv4
${lib.optionalString config.services.opendkim.enable (assert (config.services.opendkim.socket == "local:/run/opendkim/opendkim.sock"); ''
smtpd_milters = unix:/run/opendkim/opendkim.sock
non_smtpd_milters = unix:/run/opendkim/opendkim.sock
'')}
${lib.optionalString config.services.opendkim.enable (
assert (config.services.opendkim.socket == "local:/run/opendkim/opendkim.sock");
''
smtpd_milters = unix:/run/opendkim/opendkim.sock
non_smtpd_milters = unix:/run/opendkim/opendkim.sock
''
)}
'';
masterConfig."relayservice" = {
command = "smtp";
type = "unix";
args = [
"-o" "smtp_sasl_auth_enable=yes"
"-o" "smtp_sasl_security_options=noanonymous"
"-o" "smtp_tls_security_level=secure"
"-o" "smtp_sasl_password_maps=texthash:${config.sops.secrets.relay_creds.path}"
"-o" "smtp_tls_wrappermode=no"
#"-o" "relayhost=${relayhost}"
] ++ (if debug then ["-v"] else []);
"-o"
"smtp_sasl_auth_enable=yes"
"-o"
"smtp_sasl_security_options=noanonymous"
"-o"
"smtp_tls_security_level=secure"
"-o"
"smtp_sasl_password_maps=texthash:${config.sops.secrets.relay_creds.path}"
"-o"
"smtp_tls_wrappermode=no"
#"-o" "relayhost=${relayhost}"
] ++ (if debug then [ "-v" ] else [ ]);
};
masterConfig.qmgr = lib.mkIf debug { args = ["-v"]; };
masterConfig.cleanup = lib.mkIf debug { args = ["-v"]; };
masterConfig.smtpd = lib.mkIf debug { args = ["-v"]; };
masterConfig.qmgr = lib.mkIf debug { args = [ "-v" ]; };
masterConfig.cleanup = lib.mkIf debug { args = [ "-v" ]; };
masterConfig.smtpd = lib.mkIf debug { args = [ "-v" ]; };
submissionsOptions = {
smtpd_tls_key_file = config.security.acme.certs."liam.dis8.net".directory + "/key.pem";
smtpd_tls_cert_file = config.security.acme.certs."liam.dis8.net".directory + "/full.pem";
@@ -124,6 +174,5 @@ in {
tls_preempt_cipherlist = "no";
};
};
}

View File

@@ -1,4 +1,5 @@
{ lib, config, ... }: let
{ lib, config, ... }:
let
# from `curl -fsSL http://169.254.169.254/metadata/v1.json | jq '.interfaces.public[0].anchor_ipv4'`
# {
# "ip_address": "10.46.0.7",
@@ -7,20 +8,25 @@
# }
interface_conf = {
useDHCP = true;
ipv4.addresses = [{
address = "10.46.0.7";
prefixLength = 24;
}];
ipv4.routes = [{
address = "0.0.0.0";
prefixLength = 0;
via = "10.46.0.1";
options.scope = "global";
options.src = "10.46.0.7";
options.metric = "1200";
}];
ipv4.addresses = [
{
address = "10.46.0.7";
prefixLength = 24;
}
];
ipv4.routes = [
{
address = "0.0.0.0";
prefixLength = 0;
via = "10.46.0.1";
options.scope = "global";
options.src = "10.46.0.7";
options.metric = "1200";
}
];
};
in {
in
{
networking.interfaces."ens3" = lib.mkIf (!config.vacu.underTest) interface_conf;
networking.interfaces."eth0" = lib.mkIf ( config.vacu.underTest) interface_conf;
networking.interfaces."eth0" = lib.mkIf (config.vacu.underTest) interface_conf;
}

View File

@@ -1,16 +1,19 @@
{ config, ... }:
let
domains = [
"smtp.shelvacu.com"
"imap.shelvacu.com"
"mail.shelvacu.com"
"autoconfig.shelvacu.com"
"mail.dis8.net"
"liam.dis8.net"
];
domains = [
"smtp.shelvacu.com"
"imap.shelvacu.com"
"mail.shelvacu.com"
"autoconfig.shelvacu.com"
"mail.dis8.net"
"liam.dis8.net"
];
in
{
networking.firewall.allowedTCPPorts = [ 80 443 ];
networking.firewall.allowedTCPPorts = [
80
443
];
security.acme.acceptTerms = true;
security.acme.defaults.webroot = "/var/lib/acme/acme-challenge";
security.acme.defaults.email = "shelvacu@gmail.com";
@@ -31,4 +34,4 @@ in
default = true;
};
};
}
}

View File

@@ -1,4 +1,17 @@
{ config, pkgs, lib, ... }: with lib.strings; with lib.lists; let
{
pkgs,
lib,
...
}:
let
inherit (lib.strings)
concatStringsSep
splitString
match
replaceStrings
concatStrings
;
inherit (lib.lists) reverseList length elemAt;
email_folders = [
"24nm-domain@shelvacu.com"
"agora@shelvacu.com"
@@ -7,6 +20,7 @@
"paxful@shelvacu.com"
"postgres-lists@shelvacu.com"
"cpapsupplies@shelvacu.com"
"jork@shelvacu.com"
"bob@dis8.net"
"fresh.avocado@dis8.net"
@@ -18,7 +32,7 @@
"jean-luc@jean-luc.org"
"mariceayukawa@jean-luc.org"
"snow@jean-luc.org"
"capt@in.jean-luc.org"
];
domain_folders = [
@@ -32,30 +46,51 @@
"xn--tulp-yoa.info"
];
valid_ish_domain = domain: match "[a-z0-9][a-z0-9-]*(\\.[a-z0-9][a-z0-9-]*)+" domain != null;
mk_domain_folder_name = domain: assert valid_ish_domain domain; concatStringsSep "." (reverseList (splitString "." domain));
mk_email_folder_name = email: let
parts = splitString "@" email;
domain_part = assert (length parts) == 2; elemAt parts 1;
user_part = assert (length parts) == 2; elemAt parts 0;
domain_folder = mk_domain_folder_name domain_part;
folder_name = domain_folder + ".@" + user_part;
in folder_name;
mk_domain_folder_name =
domain:
assert valid_ish_domain domain;
concatStringsSep "." (reverseList (splitString "." domain));
mk_email_folder_name =
email:
let
parts = splitString "@" email;
domain_part =
assert (length parts) == 2;
elemAt parts 1;
user_part =
assert (length parts) == 2;
elemAt parts 0;
domain_folder = mk_domain_folder_name domain_part;
folder_name = domain_folder + ".@" + user_part;
in
folder_name;
is_quoteable = s: match "[ -~]*" s != null;
sieve_quote_string = s: assert is_quoteable s; "\"" + (replaceStrings ["\"" "\\"] ["\\\"" "\\\\"] s) + "\"";
email_filters = map (e:
''
elsif header :is "X-Envelope-To" ${sieve_quote_string e} {
fileinto :create ${sieve_quote_string (mk_email_folder_name e)};
}
''
) email_folders;
domain_filters = map (d:
''
elsif header :matches "X-Envelope-To" ${sieve_quote_string ("*@" + d)} {
fileinto :create ${sieve_quote_string (mk_domain_folder_name d)};
}
''
) domain_folders;
sieve_quote_string =
s:
assert is_quoteable s;
"\""
+ (replaceStrings
[
"\""
"\\"
]
[
"\\\""
"\\\\"
]
s
)
+ "\"";
email_filters = map (e: ''
elsif header :is "X-Envelope-To" ${sieve_quote_string e} {
fileinto :create ${sieve_quote_string (mk_email_folder_name e)};
}
'') email_folders;
domain_filters = map (d: ''
elsif header :matches "X-Envelope-To" ${sieve_quote_string ("*@" + d)} {
fileinto :create ${sieve_quote_string (mk_domain_folder_name d)};
}
'') domain_folders;
sieve_text = ''
require ["fileinto", "mailbox"];
@@ -70,7 +105,11 @@
${concatStrings domain_filters}
}
'';
in {
services.dovecot2.sieve.extensions = [ "fileinto" "mailbox" ];
in
{
services.dovecot2.sieve.extensions = [
"fileinto"
"mailbox"
];
services.dovecot2.sieve.scripts.before = pkgs.writeText "blargsieve" sieve_text;
}

View File

@@ -1,8 +1,11 @@
{ inputs, lib, config, ... }:
{
imports = [
inputs.sops-nix.nixosModules.sops
];
inputs,
lib,
config,
...
}:
{
imports = [ inputs.sops-nix.nixosModules.sops ];
options.vacu.secretsFolder = lib.mkOption {
type = lib.types.path;

View File

@@ -1,7 +1,6 @@
{ config, pkgs, ... }:
{
imports = [
../common/nixos.nix
./hardware-config.nix
];
@@ -9,7 +8,10 @@
boot.loader.systemd-boot.enable = true;
boot.loader.efi.canTouchEfiVariables = true;
networking.hostName = "lp0onfire"; # Define your hostname.
vacu.hostName = "lp0onfire"; # Define your hostname.
vacu.shortHostName = "lp0";
vacu.shell.color = "green";
vacu.systemKind = "server";
# Set your time zone.
time.timeZone = "America/Los_Angeles";
@@ -53,7 +55,7 @@
# system.autoUpgrade.enable = true;
# system.autoUpgrade.allowReboot = true;
# system.autoUpgrade.channel = https://nixos.org/channels/nixos-22.05-small;
nixpkgs.config.allowUnfree = true;
services.zerotierone = {
enable = true;
@@ -73,4 +75,3 @@
# internalInterfaces = [ "ztrf26rjvk" ];
# };
}

View File

@@ -1,27 +1,37 @@
# Do not modify this file! It was generated by nixos-generate-config
# and may be overwritten by future invocations. Please make changes
# to /etc/nixos/configuration.nix instead.
{ config, lib, pkgs, modulesPath, ... }:
{
config,
lib,
pkgs,
modulesPath,
...
}:
{
imports =
[ (modulesPath + "/installer/scan/not-detected.nix")
];
imports = [ (modulesPath + "/installer/scan/not-detected.nix") ];
boot.initrd.availableKernelModules = [ "xhci_pci" "ahci" "usb_storage" "usbhid" "sd_mod" ];
boot.initrd.availableKernelModules = [
"xhci_pci"
"ahci"
"usb_storage"
"usbhid"
"sd_mod"
];
boot.initrd.kernelModules = [ ];
boot.kernelModules = [ "kvm-intel" ];
boot.extraModulePackages = [ ];
fileSystems."/" =
{ device = "/dev/disk/by-uuid/51a9c6de-3231-469f-a292-ada7d2531d63";
fsType = "ext4";
};
fileSystems."/" = {
device = "/dev/disk/by-uuid/51a9c6de-3231-469f-a292-ada7d2531d63";
fsType = "ext4";
};
fileSystems."/boot" =
{ device = "/dev/disk/by-uuid/36B4-78A2";
fsType = "vfat";
};
fileSystems."/boot" = {
device = "/dev/disk/by-uuid/36B4-78A2";
fsType = "vfat";
};
swapDevices = [ ];

23
mmm/default.nix Normal file
View File

@@ -0,0 +1,23 @@
{ inputs, ... }:
{
imports = [
../common/nixos.nix
inputs.nixos-apple-silicon.nixosModules.default
./hardware.nix
];
vacu.hostName = "mmm";
vacu.shell.color = "red";
vacu.verifySystem.enable = false;
vacu.verifySystem.expectedMac = "14:98:77:3f:b8:2e";
vacu.systemKind = "server";
# asahi recommends systemd-boot
boot.loader.systemd-boot.enable = true;
boot.loader.efi.canTouchEfiVariables = false;
hardware.asahi.peripheralFirmwareDirectory = ./firmware;
services.openssh.enable = true;
system.stateVersion = "24.05";
}

BIN
mmm/firmware/all_firmware.tar.gz Executable file

Binary file not shown.

Binary file not shown.

68
mmm/hardware.nix Normal file
View File

@@ -0,0 +1,68 @@
{ lib, ... }:
let
btrfsopts = [
"noatime"
"compress=zstd"
];
in
{
boot.initrd.availableKernelModules = [
"xhci_pci"
"usbhid"
"usb_storage"
"xhci_hcd"
"uas"
];
boot.initrd.kernelModules = [ ];
boot.kernelModules = [ ];
boot.extraModulePackages = [ ];
fileSystems."/" = {
device = "/dev/disk/by-uuid/2f8b5094-94ab-4634-b11b-d4bcd2dc3f24";
fsType = "btrfs";
options = [ "subvol=root" ] ++ btrfsopts;
};
boot.initrd.luks.devices."cryptroot" = {
device = "/dev/disk/by-uuid/4e75b9ed-ac4f-48a2-b38c-c5026723171f";
# note: creation requires --new-key-file-size not --key-file-size
keyFileSize = 2048;
keyFile = "/dev/disk/by-partuuid/9d171b52-329e-4e21-9399-dcc66ff572cd";
};
fileSystems."/boot" = {
device = "/dev/disk/by-uuid/4407-1EF3";
fsType = "vfat";
options = [
"fmask=0022"
"dmask=0022"
];
};
fileSystems."/nix/store" = {
device = "/dev/disk/by-uuid/2f8b5094-94ab-4634-b11b-d4bcd2dc3f24";
fsType = "btrfs";
options = [ "subvol=nix-store" ] ++ btrfsopts;
};
fileSystems."/btrfs-root" = {
device = "/dev/disk/by-uuid/2f8b5094-94ab-4634-b11b-d4bcd2dc3f24";
fsType = "btrfs";
options = [
"subvol=/"
"noauto"
] ++ btrfsopts;
};
swapDevices = [ ];
# Enables DHCP on each ethernet and wireless interface. In case of scripted networking
# (the default) this is the recommended approach. When using systemd-networkd it's
# still possible to use this option, but it's recommended to use it in conjunction
# with explicit per-interface declarations with `networking.interfaces.<interface>.useDHCP`.
networking.useDHCP = lib.mkDefault true;
# networking.interfaces.end0.useDHCP = lib.mkDefault true;
# networking.interfaces.wlan0.useDHCP = lib.mkDefault true;
nixpkgs.hostPlatform = lib.mkDefault "aarch64-linux";
}

View File

@@ -1,11 +1,16 @@
{ config, lib, pkgs, inputs, ... }:
{
lib,
...
}:
{
imports = [
../common/nix-on-droid.nix
./flake-registry.nix
];
vacu.shell.color = "white";
vacu.systemKind = "server";
environment.etc."resolv.conf".text = lib.mkForce ''
# nameserver 10.78.79.1
nameserver 9.9.9.10
@@ -25,11 +30,11 @@
experimental-features = nix-command flakes
'';
environment.sessionVariables."PS1" = "\\w $ ";
# Set your time zone
time.timeZone = "America/Los_Angeles";
vacu.packages.yt-dlp.enable = true;
#specific to the particular install; avoids impurity
#user.gid = 10287;
#user.uid = 10287;

View File

@@ -5,5 +5,5 @@
type = "path";
path = inputs.nixpkgs.outPath;
};
nix.nixPath = [ "nxipkgs=flake:nixpkgs" ];
nix.nixPath = [ "nixpkgs=flake:nixpkgs" ];
}

35
nixvim/default.nix Normal file
View File

@@ -0,0 +1,35 @@
{ ... }:
let
in
{
opts = {
smartindent = true;
expandtab = true;
shiftwidth = 2;
softtabstop = -1;
};
plugins.comment.enable = true;
plugins.surround.enable = true;
plugins.lsp = {
enable = true;
onAttach = builtins.readFile ./nixd-init.lua;
servers = {
bashls.enable = true;
jsonls.enable = true;
# nil-ls.enable = true;
nixd = {
enable = true;
};
pyright.enable = true;
tsserver.enable = true;
lua-ls.enable = true;
rust-analyzer = {
enable = true;
installCargo = false;
installRustc = false;
};
html.enable = true;
yamlls.enable = true;
};
};
}

22
nixvim/nixd-init.lua Normal file
View File

@@ -0,0 +1,22 @@
--@param client vim.lsp.Client
local function init_per_dir_nixd(client)
if client.workspace_folders == nil then
return
end
local path = client.workspace_folders[1].name
local command = client.config.cmd[1]
local name = string.gsub(command, "(.*/)(.*)", "%2")
local is_nixd = name == "nixd"
local is_nix_stuff = (path == '/home/shelvacu/dev/nix-stuff' or path == '/home/shelvacu/nix-stuff' or path == '/data/data/com.termux.nix/files/home/nix-stuff')
if is_nixd and is_nix_stuff then
local get_flake = "(builtins.getFlake \"" .. path .. "\")"
client.config.settings["nixd"].options = {
nixos = { expr = get_flake .. ".nixosConfigurations.fw.options", },
["home-manager"] = { expr = get_flake .. ".homeConfigurations.\"nix-on-droid\".options", },
["nix-on-droid"] = { expr = get_flake .. ".nixOnDroidConfigurations.default.options", },
}
client.notify("workspace/didChangeConfiguration", { settings = client.config.settings, })
end
end
init_per_dir_nixd(client)

52
packages/bcd/default.nix Normal file
View File

@@ -0,0 +1,52 @@
{
lib,
jdk,
gradle_7,
makeWrapper,
stdenv,
fetchFromGitLab,
}:
let
gradle = gradle_7;
self = stdenv.mkDerivation rec {
pname = "bandcamp-collection-downloader";
version = "v2021-12-05";
nativeBuildInputs = [
gradle
makeWrapper
];
src = fetchFromGitLab {
domain = "framagit.org";
owner = "Ezwen";
repo = "bandcamp-collection-downloader";
rev = version;
hash = "sha256-uvfpTFt92mp4msm06Y/1Ynwx6+DiE+bR8O2dntTzj9I=";
};
mitmCache = gradle.fetchDeps {
pkg = self;
data = ./deps.json;
};
# tests want to talk to bandcamp
doCheck = false;
gradleBuildTask = "fatjar";
installPhase = ''
runHook preInstall
mkdir -p $out/{bin,share/java/bandcamp-collection-downloader}
cp build/libs/bandcamp-collection-downloader.jar $out/share/java/bandcamp-collection-downloader/bandcamp-collection-downloader.jar
makeWrapper ${lib.getExe jdk} $out/bin/bandcamp-collection-downloader \
--add-flags "-jar $out/share/java/bandcamp-collection-downloader/bandcamp-collection-downloader.jar"
runHook postInstall
'';
};
in
self

338
packages/bcd/deps.json Normal file
View File

@@ -0,0 +1,338 @@
{
"!comment": "This is a nixpkgs Gradle dependency lockfile. For more details, refer to the Gradle section in the nixpkgs manual.",
"!version": 1,
"https://plugins.gradle.org/m2": {
"com/github/gundy#semver4j/0.16.4": {
"pom": "sha256-MgAdskQ7M53SH1t5/ynRreci0boIDCFL3oGfD3LRYE0="
},
"com/github/gundy#semver4j/0.16.4/nodeps": {
"jar": "sha256-P1nspRY3TM1P01UWJb9Q+KSxkfcAUI985IZkYKYSivA="
},
"com/google/code/findbugs#jsr305/3.0.2": {
"jar": "sha256-dmrSoHg/JoeWLIrXTO7MOKKLn3Ki0IXuQ4t4E+ko0Mc=",
"pom": "sha256-GYidvfGyVLJgGl7mRbgUepdGRIgil2hMeYr+XWPXjf4="
},
"com/google/code/gson#gson-parent/2.8.6": {
"pom": "sha256-NzZGOFnsGSZyleiUlAroKo9oRBMDESL+Nc58/34wp3Q="
},
"com/google/code/gson#gson/2.8.6": {
"jar": "sha256-yPtIOQVNKAswM/gA0fWpfeLwKOuLoutFitKH5Tbz8l8=",
"pom": "sha256-IXRBWmRzMtMP2gS9HPxwij7MhOr3UX9ZYYjYJE4QORE="
},
"com/google/errorprone#error_prone_annotations/2.3.4": {
"jar": "sha256-uvfW6pfOYGxT4RtoVLpfLOfvXCTd3wr6GNEmC9JbACw=",
"pom": "sha256-EyZziktPfMrPYHuGahH7hRk+9g9qWUYRh85yZfm+W+0="
},
"com/google/errorprone#error_prone_parent/2.3.4": {
"pom": "sha256-QElbQ3pg0jmPD9/AVLidnDlKgjR6J0oHIcLpUKQwIYY="
},
"com/google/guava#failureaccess/1.0.1": {
"jar": "sha256-oXHuTHNN0tqDfksWvp30Zhr6typBra8x64Tf2vk2yiY=",
"pom": "sha256-6WBCznj+y6DaK+lkUilHyHtAopG1/TzWcqQ0kkEDxLk="
},
"com/google/guava#guava-parent/26.0-android": {
"pom": "sha256-+GmKtGypls6InBr8jKTyXrisawNNyJjUWDdCNgAWzAQ="
},
"com/google/guava#guava-parent/29.0-jre": {
"pom": "sha256-alf54C9436L0vaNBYGWmRCauG2beIoz24Zbi4ZElU78="
},
"com/google/guava#guava/29.0-jre": {
"jar": "sha256-sixftm1h57lSJTHQSy+RW1FY6AqgtA7nKCyL+wew2iU=",
"pom": "sha256-kCfpNAmJA9KH8bphyLZfAdHR4dp6b7zAS/PeBUQBRCY="
},
"com/google/guava#listenablefuture/9999.0-empty-to-avoid-conflict-with-guava": {
"jar": "sha256-s3KgN9QjCqV/vv/e8w/WEj+cDC24XQrO0AyRuXTzP5k=",
"pom": "sha256-GNSx2yYVPU5VB5zh92ux/gXNuGLvmVSojLzE/zi4Z5s="
},
"com/google/j2objc#j2objc-annotations/1.3": {
"jar": "sha256-Ia8wySJnvWEiwOC00gzMtmQaN+r5VsZUDsRx1YTmSns=",
"pom": "sha256-X6yoJLoRW+5FhzAzff2y/OpGui/XdNQwTtvzD6aj8FU="
},
"de/undercouch#gradle-download-task/4.1.1": {
"jar": "sha256-6wi1cOQI1GRnBecKlJYU1DnqKxFFXxZSqwMw3olU2rk=",
"pom": "sha256-EQnx9xpUJU1ZAzfYudRD+d/AhyjJwdgzVlXMHcyIwLk="
},
"org/checkerframework#checker-qual/2.11.1": {
"jar": "sha256-AVIkpLHcbebaBTJz1Np9Oc/qIOYwOBafxFrA0dycWTg=",
"pom": "sha256-zy4MkNj3V0VfSiWOpglzkFNmO9XaannZvVP5NaR955w="
},
"org/jetbrains/intellij/deps#trove4j/1.0.20181211": {
"jar": "sha256-r/t8haPIe9z2n/HbuE3hH2PckxKTk0vAjNerGN4INgE=",
"pom": "sha256-MQpqotkFNMMrj0bx/JjNDtrpXc38oj4oR+Xvqa4MAZo="
},
"org/jetbrains/kotlin#kotlin-android-extensions/1.5.31": {
"jar": "sha256-aO1mp5A4wtK1Tu7KFpXUuXCV4jW5DT0/WKHE3hme0lU=",
"pom": "sha256-LgIHPvU+pggMAM+KqkdItBkXpNpsSdKNaDLWoSmnzEY="
},
"org/jetbrains/kotlin#kotlin-annotation-processing-gradle/1.5.31": {
"jar": "sha256-4nC48GUtl5pjrKTUohJwmGqvBjeOLrg48Azgk5D1q0w=",
"pom": "sha256-bBvZhwcdN3Qu809UrUQ5nmuQiR4/uLDCz0qMN3Y7jVA="
},
"org/jetbrains/kotlin#kotlin-build-common/1.5.31": {
"jar": "sha256-N4s/SEMiUQ1ozWlPksWuASxrssatmVhShVOWkptVOEk=",
"pom": "sha256-ta6dsXnXsWsa9u3FHwX5rA1u+fYUm8CNiVhIphLSCY4="
},
"org/jetbrains/kotlin#kotlin-compiler-embeddable/1.5.31": {
"jar": "sha256-45gRqeTBAud5xlnu/pCwQcZs6HV4wb/awHz1BNFVF0U=",
"pom": "sha256-1Ess6vKEuuky15hYHkIrtr0sjln084u9H+Kh2lo8dTQ="
},
"org/jetbrains/kotlin#kotlin-compiler-runner/1.5.31": {
"jar": "sha256-/UvVYjtsKVsHYhlumb5xVPHvCtM4zXm7r6T7wvHACwg=",
"pom": "sha256-N16wYQP23mQGWw9CwtZtEHFZs+kvXqLhzrJRfia6yCw="
},
"org/jetbrains/kotlin#kotlin-daemon-client/1.5.31": {
"jar": "sha256-6oITtcl0wSVzoYu7dZV5hztt8XgAvbjYsFL8NS4R+cA=",
"pom": "sha256-cA50WnFGgWov+xJmkZymNq2dAioH4doKVlibE5R+ST8="
},
"org/jetbrains/kotlin#kotlin-daemon-embeddable/1.5.31": {
"jar": "sha256-9h6vieXjhIYxZQslzftm/oyuAoGgVNnZhnFgAKFbqNY=",
"pom": "sha256-alUadKuKIMrt+a281OvpYzPqq13+NV+RuwFRbMMct3Y="
},
"org/jetbrains/kotlin#kotlin-gradle-plugin-api/1.5.31": {
"jar": "sha256-j9I46omSPn3xs3X5GHEApxTH4lP3hskqrJH/BGfu8tQ=",
"pom": "sha256-QBBV9PNHv/N03+YeO9et0gvB5+YhW0RZDZRtDEfOXog="
},
"org/jetbrains/kotlin#kotlin-gradle-plugin-model/1.5.31": {
"jar": "sha256-Tl42xb32B1GAXBveqDQRBmeOYj8KrLbaKz0gTN9BBmE=",
"pom": "sha256-x/F3wK/XKh+7yWtS1V/QzsgfCMm2Sln09FFaV9+Sy7s="
},
"org/jetbrains/kotlin#kotlin-gradle-plugin/1.5.31": {
"jar": "sha256-EsFFQSMeiBzbBKw0lgV1X/D3hY0VsZ9TbAELGxPDbAw=",
"pom": "sha256-YGdxue42D9zlv4aOrVLhRcUwy0tly7VrWwImbWxsU/w="
},
"org/jetbrains/kotlin#kotlin-klib-commonizer-api/1.5.31": {
"jar": "sha256-EDlqWVu4xeJUkDAxDTDNUWd8WIBCFqUoI6SAaBnLD9c=",
"pom": "sha256-6g+LFK3jOqvoJEhLpnA3UV5OuId0zVfneQqFQbWHQpk="
},
"org/jetbrains/kotlin#kotlin-native-utils/1.5.31": {
"jar": "sha256-cSfgacEGNt54QsP4TC7G4/W3dk+m3f3rE5XLvxrlUcQ=",
"pom": "sha256-aFn8z6JTCGmRPaiac3gOpgCqaXFfFHRZdvL7BbLj3oc="
},
"org/jetbrains/kotlin#kotlin-project-model/1.5.31": {
"jar": "sha256-rcqYHKsdnQUtjiNnMAJ2bUp5TMeOtfb+skEstpy8HNE=",
"pom": "sha256-3wmxdZNSUpS80PdsR4eGcuAKLhsYH3B0lrHUE5C8Ruk="
},
"org/jetbrains/kotlin#kotlin-scripting-common/1.5.31": {
"jar": "sha256-IZ7fAK7YKIxx2AAvFZhS1TXsmveuv7B9+DboR5qDR+8=",
"pom": "sha256-LSB1cya+WOSOs2EE1i0LyL/Z3Ogm2M3QXLThlgnFlTI="
},
"org/jetbrains/kotlin#kotlin-scripting-compiler-embeddable/1.5.31": {
"jar": "sha256-yGIfrjb42bhJFqpMBH0pgWX6Mv09ID0W0mUd5JGoRT0=",
"pom": "sha256-CYeCsKIsAhdU0NKXANquyn/HYEIIL+HZDcY8lfJiYlE="
},
"org/jetbrains/kotlin#kotlin-scripting-compiler-impl-embeddable/1.5.31": {
"jar": "sha256-elvIU0hD4LAcY1+Ys8WLLQMDx/GocxW39EImuTry5nM=",
"pom": "sha256-GMfKFcag0wZNkA5sxntadv3pMNA5PdNCzOTUN76wc/c="
},
"org/jetbrains/kotlin#kotlin-scripting-jvm/1.5.31": {
"jar": "sha256-b65w7F2DcwrUfQEt3iMNbdSXXD2MDomt7Jq9Q/pv5t4=",
"pom": "sha256-HPr0zKwkDc2NC2xhM7vGVAgc28CDJx+Pn8lxH4BctPA="
},
"org/jetbrains/kotlin#kotlin-tooling-metadata/1.5.31": {
"jar": "sha256-DdebRc2fJw+N9e68t8jWriNOmCdNGhm+aiSu4SpOOr4=",
"pom": "sha256-n8mlg2Mc6fd9bWFK35erK4IM/X71Xa5LFRqDlre6bps="
},
"org/jetbrains/kotlin#kotlin-util-io/1.5.31": {
"jar": "sha256-LCbUBlmFc+qr1XUCnw/+G807aZvwJScJNYSo0nbPUmo=",
"pom": "sha256-+pgbeSjlucTwdec+CBgsXj236IWpEPNl+2Ku+I5aNVo="
},
"org/jetbrains/kotlin#kotlin-util-klib/1.5.31": {
"jar": "sha256-+RcvLoQZS9Wp1Al8f/3Pf/wLwiMi0OH+FwG2KsM613A=",
"pom": "sha256-O5q77lvcFo+l8EOXgLdIBWm6DRjbNPdJHoqsX/1odjM="
},
"org/jetbrains/kotlin/jvm#org.jetbrains.kotlin.jvm.gradle.plugin/1.5.31": {
"pom": "sha256-TwiJBgIxZmuJn35gfMdxmxvrMMxt7Opn00q97RO2lBM="
},
"org/jetbrains/kotlinx#kotlinx-coroutines-core-jvm/1.5.0": {
"jar": "sha256-eNbMcTX4TWkv83Uvz9H6G74JQNffcGUuTx6u7Ax4r7s=",
"module": "sha256-yIXdAoEHbFhDgm3jF+PLzcPYhZ2+71OuHPrNG5xg+W4=",
"pom": "sha256-U2IuA3eN+EQPwBIgGjW7S9/kAWTv7GErvvze7LL/wqs="
},
"org/jetbrains/kotlinx#kotlinx-coroutines-core/1.5.0": {
"module": "sha256-2KJqiW2jL7H4w/E/5By3mKYSocHd86VV2C7h/xbvE9M=",
"pom": "sha256-/8k2P3ybw40mHJOM23+kXO5WiU1xq7Kd+/23CzVY1FI="
},
"org/sonatype/oss#oss-parent/7": {
"pom": "sha256-tR+IZ8kranIkmVV/w6H96ne9+e9XRyL+kM5DailVlFQ="
},
"org/sonatype/oss#oss-parent/9": {
"pom": "sha256-+0AmX5glSCEv+C42LllzKyGH7G8NgBgohcFO8fmCgno="
}
},
"https://repo.maven.apache.org/maven2": {
"com/google/code/gson#gson-parent/2.8.8": {
"pom": "sha256-IRPa1JelW3F03dXKUG9C4RKZHP7Mdt9icd8RWOPwmm8="
},
"com/google/code/gson#gson/2.8.8": {
"jar": "sha256-xvMVKww5wbfr4mfplgSnUOnVWFsvPy4Z1vvX7JCA0Ps=",
"pom": "sha256-NmyNW7OsBqHbLU7189l5bjCBuz+fDzmMxX+a+82cWDM="
},
"com/sun/mail#all/1.6.2": {
"pom": "sha256-S36Dqpt31l4AfpfLUPm4nNt1T6rxZBHl/ZTR49q3brM="
},
"com/sun/mail#javax.mail/1.6.2": {
"jar": "sha256-RbUV5xBJRMCeRbnHuxzl3/ZASGN0hS3SsugMw3Ut+hE=",
"pom": "sha256-xCKcBbWDbwAlITY9NDXz0HJmJ0RUi/F+fnreyv5ouf0="
},
"info/picocli#picocli/4.6.1": {
"jar": "sha256-Km4DMQ2xSfihHrBYqnjndcIp74FjM8loc3l2LSKDOtY=",
"pom": "sha256-sQOC7VBz9mKP84EayWFEkbHv8wLDz55Cmo81P2w75M8="
},
"javax/activation#activation/1.1": {
"jar": "sha256-KIHHnJ1u8BxY5ivuoT6dGsi4uqFvL8GYrW5ndt79zdM=",
"pom": "sha256-1JDlQKEVBLnXFxixyF/vez3mgCNhKQgkU5sHbVj6qKA="
},
"net/java#jvnet-parent/1": {
"pom": "sha256-KBRAgRJo5l2eJms8yJgpfiFOBPCXQNA4bO60qJI9Y78="
},
"org/apiguardian#apiguardian-api/1.1.2": {
"jar": "sha256-tQlEisUG1gcxnxglN/CzXXEAdYLsdBgyofER5bW3Czg=",
"module": "sha256-4IAoExN1s1fR0oc06aT7QhbahLJAZByz7358fWKCI/w=",
"pom": "sha256-MjVQgdEJCVw9XTdNWkO09MG3XVSemD71ByPidy5TAqA="
},
"org/ini4j#ini4j/0.5.4": {
"jar": "sha256-qtYGNe7lZyVO0p8Y+xjA+eTE2s9RyCKRKCAxg7s14t0=",
"pom": "sha256-XMYUkRJoPvybUbn9k3h307NQPfboBdMHHOTbOb41mY8="
},
"org/jetbrains#annotations/13.0": {
"jar": "sha256-rOKhDcji1f00kl7KwD5JiLLA+FFlDJS4zvSbob0RFHg=",
"pom": "sha256-llrrK+3/NpgZvd4b96CzuJuCR91pyIuGN112Fju4w5c="
},
"org/jetbrains/intellij/deps#trove4j/1.0.20181211": {
"jar": "sha256-r/t8haPIe9z2n/HbuE3hH2PckxKTk0vAjNerGN4INgE=",
"pom": "sha256-MQpqotkFNMMrj0bx/JjNDtrpXc38oj4oR+Xvqa4MAZo="
},
"org/jetbrains/kotlin#kotlin-compiler-embeddable/1.5.31": {
"jar": "sha256-45gRqeTBAud5xlnu/pCwQcZs6HV4wb/awHz1BNFVF0U=",
"pom": "sha256-1Ess6vKEuuky15hYHkIrtr0sjln084u9H+Kh2lo8dTQ="
},
"org/jetbrains/kotlin#kotlin-daemon-embeddable/1.5.31": {
"jar": "sha256-9h6vieXjhIYxZQslzftm/oyuAoGgVNnZhnFgAKFbqNY=",
"pom": "sha256-alUadKuKIMrt+a281OvpYzPqq13+NV+RuwFRbMMct3Y="
},
"org/jetbrains/kotlin#kotlin-klib-commonizer-embeddable/1.5.31": {
"jar": "sha256-hQ3nvEsAp4jnRUPZRAlrcHkLvL6XaNQtAQRbMhBXbnE=",
"pom": "sha256-EtXpQVih6CA4YFUeyuUiiiM75NrhtRmvJLDEUui7wsc="
},
"org/jetbrains/kotlin#kotlin-reflect/1.5.31": {
"jar": "sha256-bg9UkOa5ZJ3dJnBTTk06A70oPDNYuO710TBP1filpPs=",
"pom": "sha256-VitLqu6sfHJYlKEF/FHNPWfgolnnEUDVVUJsMycLMBQ="
},
"org/jetbrains/kotlin#kotlin-script-runtime/1.5.31": {
"jar": "sha256-JORQ/udkXtNZCYHd3M85fA2eu3JYFclMT1Vcw9svn5Y=",
"pom": "sha256-+MNYzwUXT+VmQWKGI7oxfJ3DcODp3oBbCLnRGMPFhbc="
},
"org/jetbrains/kotlin#kotlin-scripting-common/1.5.31": {
"jar": "sha256-IZ7fAK7YKIxx2AAvFZhS1TXsmveuv7B9+DboR5qDR+8=",
"pom": "sha256-LSB1cya+WOSOs2EE1i0LyL/Z3Ogm2M3QXLThlgnFlTI="
},
"org/jetbrains/kotlin#kotlin-scripting-compiler-embeddable/1.5.31": {
"jar": "sha256-yGIfrjb42bhJFqpMBH0pgWX6Mv09ID0W0mUd5JGoRT0=",
"pom": "sha256-CYeCsKIsAhdU0NKXANquyn/HYEIIL+HZDcY8lfJiYlE="
},
"org/jetbrains/kotlin#kotlin-scripting-compiler-impl-embeddable/1.5.31": {
"jar": "sha256-elvIU0hD4LAcY1+Ys8WLLQMDx/GocxW39EImuTry5nM=",
"pom": "sha256-GMfKFcag0wZNkA5sxntadv3pMNA5PdNCzOTUN76wc/c="
},
"org/jetbrains/kotlin#kotlin-scripting-jvm/1.5.31": {
"jar": "sha256-b65w7F2DcwrUfQEt3iMNbdSXXD2MDomt7Jq9Q/pv5t4=",
"pom": "sha256-HPr0zKwkDc2NC2xhM7vGVAgc28CDJx+Pn8lxH4BctPA="
},
"org/jetbrains/kotlin#kotlin-stdlib-common/1.5.31": {
"jar": "sha256-36KhjiawKDiO4ZaNGZv28Wb3N6twScJaXi2mFEBOIq0=",
"pom": "sha256-thXpRrjD0r6pllLs2pfVfs+Dv180xl0oZ5CvI+USg8I="
},
"org/jetbrains/kotlin#kotlin-stdlib-jdk7/1.5.0": {
"jar": "sha256-rBLwkvErV1wfngq1AlseYQsP6VZj4mNxwWwyiJVxG64=",
"pom": "sha256-7T5s00w9Onc9oOAHuxLhZFSHJUZOWtthZEqY+yklStE="
},
"org/jetbrains/kotlin#kotlin-stdlib-jdk7/1.5.31": {
"jar": "sha256-olv0c1POiZ2EPL3e5RbWIac0c+f7qX+NAwHntK7XwV8=",
"pom": "sha256-IxOEie4pOmgZcGiHd0X3AL+hGvmJGHvtPDB0zYwHl3g="
},
"org/jetbrains/kotlin#kotlin-stdlib-jdk8/1.5.0": {
"jar": "sha256-FebIG56EXu/ljVGgRnC7kEGARvRYJk7A5h7pvbwb+uc=",
"pom": "sha256-0Ls+nTxj4e2bB3lPhWtyIEJwVxffMFEOTM4RPuLKWU0="
},
"org/jetbrains/kotlin#kotlin-stdlib-jdk8/1.5.31": {
"jar": "sha256-tUj3dnqs8CnSQX5HRAdCvW0+vt4ZtgOG4jVUzlxMX9w=",
"pom": "sha256-RREKqwB0eSuBWAewKy2vGNKzfodHrAaSqteg0C2ok98="
},
"org/jetbrains/kotlin#kotlin-stdlib/1.5.31": {
"jar": "sha256-SADOrLLsC7mVmghxVLjjUxjq0epOujLUuxuXNCIqfmg=",
"pom": "sha256-j3Z2AQSsTocwCcnwM90brXW507j5Uh1j2xJk2ESFLmw="
},
"org/jetbrains/kotlinx#kotlinx-coroutines-core-jvm/1.5.0": {
"jar": "sha256-eNbMcTX4TWkv83Uvz9H6G74JQNffcGUuTx6u7Ax4r7s=",
"module": "sha256-yIXdAoEHbFhDgm3jF+PLzcPYhZ2+71OuHPrNG5xg+W4=",
"pom": "sha256-U2IuA3eN+EQPwBIgGjW7S9/kAWTv7GErvvze7LL/wqs="
},
"org/jetbrains/kotlinx#kotlinx-coroutines-core/1.5.0": {
"module": "sha256-2KJqiW2jL7H4w/E/5By3mKYSocHd86VV2C7h/xbvE9M=",
"pom": "sha256-/8k2P3ybw40mHJOM23+kXO5WiU1xq7Kd+/23CzVY1FI="
},
"org/jsoup#jsoup/1.14.3": {
"jar": "sha256-kq8Z7FfMd2N9tEkPD1AR8ERNNTIJzjYIO6xCj5uBo5w=",
"pom": "sha256-UsW86oFXCKOWqs6xQZm5Z5j8MhmtBSNvAaKttMhekGE="
},
"org/junit#junit-bom/5.8.1": {
"module": "sha256-a4LLpSoTSxPBmC8M+WIsbUhTcdQLmJJG8xJOOwpbGFQ=",
"pom": "sha256-733Ef45KFoZPR3lyjofteFOYGeT7iSdoqdprjvkD+GM="
},
"org/junit/jupiter#junit-jupiter-api/5.8.1": {
"jar": "sha256-zjN0p++6YF4tK2mj/vkBNAMrqz7MPthXmkhxscLEcpw=",
"module": "sha256-DWnbwja33Kq0ynNpqlYOmwqbvvf5WIgv+0hTPLunwJ0=",
"pom": "sha256-d61+1KYwutH8h0agpuZ1wj+2lAsnq2LMyzTk/Pz+Ob8="
},
"org/junit/jupiter#junit-jupiter-engine/5.8.1": {
"jar": "sha256-Rom8kCJVoZ/pgndoO6MjHAlNEHxUyNNfK2+cl9ImQY4=",
"module": "sha256-aHkP7DP5ew7IQM9HrEDuDHLgVvEiyg88ZkZ0M0mTdpk=",
"pom": "sha256-qjIKMYpyceMyYsSA/POZZbmobap2Zm63dTQrgOnN1F4="
},
"org/junit/platform#junit-platform-commons/1.8.1": {
"jar": "sha256-+k+mjIvVTdDLScP8vpsuQvTaa+2+fnzPKgXxoeYJtZM=",
"module": "sha256-aY/QVBrLfv/GZZhI/Qx91QEKSfFfDBy6Q+U1gH+Q9ms=",
"pom": "sha256-4ZcoLlLnANEriJie3FSJh0aTUC5KqJB6zwgpgBq6bUQ="
},
"org/junit/platform#junit-platform-engine/1.8.1": {
"jar": "sha256-cCho7X6GubRnLt4PHhhekFusqa+rV3RqfGUL48e8oEc=",
"module": "sha256-2fQgpkU5o+32D4DfDG/XIrdQcldEx5ykD30lrlbKS6Q=",
"pom": "sha256-hqrU5ld1TkOgDfIm3VTIrsHsarZTP1ASGQfkZi3i5fI="
},
"org/opentest4j#opentest4j/1.2.0": {
"jar": "sha256-WIEt5giY2Xb7ge87YtoFxmBMGP1KJJ9QRCgkefwoavI=",
"pom": "sha256-qW5nGBbB/4gDvex0ySQfAlvfsnfaXStO4CJmQFk2+ZQ="
},
"org/slf4j#slf4j-api/1.6.6": {
"pom": "sha256-cxmZMiteIokinNntRiTJQexXG3xh0qJ9alB+9zuXyho="
},
"org/slf4j#slf4j-api/1.7.32": {
"jar": "sha256-NiT4R0wa9G11+YvAl9eGSjI8gbOAiqQ2iabhxgHAJ74=",
"pom": "sha256-ABzeWzxrqRBwQlz+ny5pXkrri8KQotTNllMRJ6skT+U="
},
"org/slf4j#slf4j-parent/1.6.6": {
"pom": "sha256-QrjCR2CP2OENW2Zs98gKW1nSseEoRQ97bZ0sIM+2sxs="
},
"org/slf4j#slf4j-parent/1.7.32": {
"pom": "sha256-WrNJ0PTHvAjtDvH02ThssZQKL01vFSFQ4W277MC4PHA="
},
"org/slf4j#slf4j-simple/1.7.32": {
"jar": "sha256-0v3XtzyiAZogYtFFoNhheaWPmMjD41ynxzWieztWIcM=",
"pom": "sha256-VVTmGS0A/7oRfST9+HBIj50DkABH6Lq1XgDugzgvQdg="
},
"org/sonatype/oss#oss-parent/7": {
"pom": "sha256-tR+IZ8kranIkmVV/w6H96ne9+e9XRyL+kM5DailVlFQ="
},
"org/sonatype/oss#oss-parent/9": {
"pom": "sha256-+0AmX5glSCEv+C42LllzKyGH7G8NgBgohcFO8fmCgno="
},
"org/xerial#sqlite-jdbc/3.36.0.2": {
"jar": "sha256-D++S/Lco+7Tw88ua2+cIgjuGB0zef46jkd/AZiwz7Lo=",
"pom": "sha256-IQG6KV0YmqEcASDMVuEs4WoyC5EE9gBer03ud4gXAkk="
},
"org/zeroturnaround#zt-zip/1.14": {
"jar": "sha256-lkDsuPjrnDFVsVbtu0BJyT3uXaKz31U6UdlGmK+3aNk=",
"pom": "sha256-esRAYySqeauHFiEV/lpCdp4yB8eCFbvCMZ2ZNeNV5hg="
}
}
}

View File

@@ -15,90 +15,110 @@
writeText,
lib,
}@args:
stdenv.mkDerivation (self: let
# this script depends on an old version of libsmi's smistrip
libsmi = stdenv.mkDerivation rec {
pname = "libsmi";
version = "0.4.8";
stdenv.mkDerivation (
self:
let
# this script depends on an old version of libsmi's smistrip
libsmi = stdenv.mkDerivation rec {
pname = "libsmi";
version = "0.4.8";
src = fetchurl {
url = "https://www.ibr.cs.tu-bs.de/projects/libsmi/download/${pname}-${version}.tar.gz";
hash = "sha256-8EilJw9BvIiww7Co/nDKTXFqRrUxoOyqqHxGL0nXSEk=";
};
src = fetchurl {
url = "https://www.ibr.cs.tu-bs.de/projects/libsmi/download/${pname}-${version}.tar.gz";
hash = "sha256-8EilJw9BvIiww7Co/nDKTXFqRrUxoOyqqHxGL0nXSEk=";
};
env.NIX_CFLAGS_COMPILE = "-std=gnu90";
#env.CFLAGS="-Wno-error";
#env.NIX_DEBUG="7";
env.NIX_CFLAGS_COMPILE = "-std=gnu90";
#env.CFLAGS="-Wno-error";
#env.NIX_DEBUG="7";
hardeningDisable = [ "format" ];
hardeningDisable = [ "format" ];
meta = with lib; {
description = "A Library to Access SMI MIB Information";
homepage = "https://www.ibr.cs.tu-bs.de/projects/libsmi/index.html";
license = licenses.free;
platforms = lib.platforms.linux ++ lib.platforms.darwin;
};
};
in rec {
pname = "snmp-mibs-downloader";
version = "1.6";
meta = with lib; {
description = "A Library to Access SMI MIB Information";
homepage = "https://www.ibr.cs.tu-bs.de/projects/libsmi/index.html";
license = licenses.free;
platforms = lib.platforms.linux ++ lib.platforms.darwin;
};
};
in
rec {
pname = "snmp-mibs-downloader";
version = "1.6";
src = fetchFromGitLab {
domain = "salsa.debian.org";
owner = "debian";
repo = "${pname}";
rev = "debian/${version}";
hash = "sha256-W2VW3EJWmHwlqMoL12dFcfkYmAADLOtUWCydcL5qUKc=";
};
src = fetchFromGitLab {
domain = "salsa.debian.org";
owner = "debian";
repo = "${pname}";
rev = "debian/${version}";
hash = "sha256-W2VW3EJWmHwlqMoL12dFcfkYmAADLOtUWCydcL5qUKc=";
};
# installPhase = ''
# install -Dm755 download-mibs $out/bin
# install -Dm644 *.conf *list $out/etc/snmp-mips-downloader
# cp mibrfcs/* $out/share/snmp/mibs-downloader/mibrfcs
# cp mibiana/* $out/share/snmp/mibs-downloader/mibiana
# gzip -9 $out/share/snmp/mibs-downloader/*/*
# installPhase = ''
# install -Dm755 download-mibs $out/bin
# install -Dm644 *.conf *list $out/etc/snmp-mips-downloader
# cp mibrfcs/* $out/share/snmp/mibs-downloader/mibrfcs
# cp mibiana/* $out/share/snmp/mibs-downloader/mibiana
# gzip -9 $out/share/snmp/mibs-downloader/*/*
# '';
postPatch = ''
substituteInPlace download-mibs \
--replace-fail SMISTRIP=/usr/bin/smistrip "" \
--replace-fail CONFDIR=/etc/snmp-mibs-downloader "BASEDIR=/var/lib/mibs; AUTOLOAD='rfc ianarfc iana'" \
--replace-fail '. $CONFDIR/snmp-mibs-downloader.conf' ""
'';
preInstall = ''
mkdir -p $out/usr/bin $out/etc/snmp-mibs-downloader $out/usr/share/snmp/mibs-downloader/mib{rfcs,iana} $out/usr/share/snmp/mibs
'';
installFlags = [ "INSTALL=install" "DESTDIR=$(out)" ];
postInstall = ''
mv $out/usr/* $out
rmdir $out/usr
substituteInPlace $out/etc/snmp-mibs-downloader/* \
--replace-quiet 'DIR=/usr/share/snmp/mibs-downloader' 'DIR='$out'/share/snmp/mibs-downloader'
mv $out/bin/download-mibs $out/bin/.download-mibs-unwrapped
cat <<EOF > $out/bin/download-mibs
#!${bash}/bin/bash
PATH=${lib.escapeShellArg (lib.concatStringsSep ":" (lib.flip map [ coreutils gzip gnutar unzip wget gnupatch ] (p: "${p}/bin")))}
SMISTRIP=${libsmi}/bin/smistrip
CONFDIR=$out/etc/snmp-mibs-downloader
source $out/bin/.download-mibs-unwrapped
EOF
chmod u+x $out/bin/download-mibs
'';
# '';
postPatch = ''
substituteInPlace download-mibs \
--replace-fail SMISTRIP=/usr/bin/smistrip "" \
--replace-fail CONFDIR=/etc/snmp-mibs-downloader "BASEDIR=/var/lib/mibs; AUTOLOAD='rfc ianarfc iana'" \
--replace-fail '. $CONFDIR/snmp-mibs-downloader.conf' ""
'';
preInstall = ''
mkdir -p $out/usr/bin $out/etc/snmp-mibs-downloader $out/usr/share/snmp/mibs-downloader/mib{rfcs,iana} $out/usr/share/snmp/mibs
'';
installFlags = [
"INSTALL=install"
"DESTDIR=$(out)"
];
postInstall = ''
mv $out/usr/* $out
rmdir $out/usr
substituteInPlace $out/etc/snmp-mibs-downloader/* \
--replace-quiet 'DIR=/usr/share/snmp/mibs-downloader' 'DIR='$out'/share/snmp/mibs-downloader'
mv $out/bin/download-mibs $out/bin/.download-mibs-unwrapped
cat <<EOF > $out/bin/download-mibs
#!${bash}/bin/bash
PATH=${
lib.escapeShellArg (
lib.concatStringsSep ":" (
lib.flip map [
coreutils
gzip
gnutar
unzip
wget
gnupatch
] (p: "${p}/bin")
)
)
}
SMISTRIP=${libsmi}/bin/smistrip
CONFDIR=$out/etc/snmp-mibs-downloader
source $out/bin/.download-mibs-unwrapped
EOF
chmod u+x $out/bin/download-mibs
'';
env.NIX_DEBUG="7";
# solutions.default = {
# scripts = [ "bin/download-mibs" ];
# interpreter = "${bash}/bin/bash";
# inputs = [ coreutils gzip gnutar unzip wget gnupatch ];
# keep = {
# "$archive_fetcher" = true;
# source = [ "$CONFDIR/$i.conf" ];
# "${wget}/bin/wget" = true;
# };
# fix = { "$SMISTRIP" = [ "${libsmi}/bin/smistrip" ]; };
# };
env.NIX_DEBUG = "7";
# solutions.default = {
# scripts = [ "bin/download-mibs" ];
# interpreter = "${bash}/bin/bash";
# inputs = [ coreutils gzip gnutar unzip wget gnupatch ];
# keep = {
# "$archive_fetcher" = true;
# source = [ "$CONFDIR/$i.conf" ];
# "${wget}/bin/wget" = true;
# };
# fix = { "$SMISTRIP" = [ "${libsmi}/bin/smistrip" ]; };
# };
meta = {
mainProgram = "download-mibs";
};
})
meta = {
mainProgram = "download-mibs";
};
}
)

View File

@@ -12,113 +12,122 @@
breakpointHook,
}@args:
stdenv.mkDerivation (finalAttrs: let
# ./configure --disable-shared --disable-yang --with-pathseparator=';' --with-dirseparator='/' --with-smipath=${INSTALL_PREFIX}'/${SHARE}/snmpb/mibs;'${INSTALL_PREFIX}'/${SHARE}/snmpb/pibs'
libsmi = finalAttrs.passthru.libsmi;
# $(INSTALL) -m 444 ${ROOT_OWNER} libsmi/mibs/iana/* ${INSTALL_PREFIX}/${SHARE}/snmpb/mibs
# $(INSTALL) -m 444 ${ROOT_OWNER} libsmi/mibs/ietf/* ${INSTALL_PREFIX}/${SHARE}/snmpb/mibs
# $(INSTALL) -m 444 ${ROOT_OWNER} libsmi/mibs/tubs/* ${INSTALL_PREFIX}/${SHARE}/snmpb/mibs
# $(INSTALL) -m 444 ${ROOT_OWNER} libsmi/pibs/ietf/* ${INSTALL_PREFIX}/${SHARE}/snmpb/pibs
# $(INSTALL) -m 444 ${ROOT_OWNER} libsmi/pibs/tubs/* ${INSTALL_PREFIX}/${SHARE}/snmpb/pibs
stdenv.mkDerivation (
finalAttrs:
let
# ./configure --disable-shared --disable-yang --with-pathseparator=';' --with-dirseparator='/' --with-smipath=${INSTALL_PREFIX}'/${SHARE}/snmpb/mibs;'${INSTALL_PREFIX}'/${SHARE}/snmpb/pibs'
libsmi = finalAttrs.passthru.libsmi;
# $(INSTALL) -m 444 ${ROOT_OWNER} libsmi/mibs/iana/* ${INSTALL_PREFIX}/${SHARE}/snmpb/mibs
# $(INSTALL) -m 444 ${ROOT_OWNER} libsmi/mibs/ietf/* ${INSTALL_PREFIX}/${SHARE}/snmpb/mibs
# $(INSTALL) -m 444 ${ROOT_OWNER} libsmi/mibs/tubs/* ${INSTALL_PREFIX}/${SHARE}/snmpb/mibs
# $(INSTALL) -m 444 ${ROOT_OWNER} libsmi/pibs/ietf/* ${INSTALL_PREFIX}/${SHARE}/snmpb/pibs
# $(INSTALL) -m 444 ${ROOT_OWNER} libsmi/pibs/tubs/* ${INSTALL_PREFIX}/${SHARE}/snmpb/pibs
in {
pname = "snmpb";
version = "0.9pre1";
in
{
pname = "snmpb";
version = "0.9pre1";
# __structuredAttrs = true;
# __structuredAttrs = true;
passthru = {
proFile = "${finalAttrs.pname}.pro";
makeFile = "makefile.${finalAttrs.pname}";
smipath = "${finalAttrs.passthru.libsmi-data}/share/snmpb/mibs;${finalAttrs.passthru.libsmi-data}/share/snmpb/pibs";
libsmi = args.libsmi.overrideAttrs (final: prev: {
#preConfigure = (prev.preConfigure or "") + "\n" + ''
# appendToVar configureFlags --prefix=$out/ --disable-yang --with-pathseparator=';' --with-dirseparator='/'
#'';
configureFlags = (prev.configureFlags or []) ++ ["--with-pathseparator=;" "--with-smipath=${finalAttrs.passthru.smipath}"];
env.NIX_DEBUG="2";
pname = prev.pname + "-for-snmpb";
});
libsmi-data = stdenv.mkDerivation {
name = "libsmi-snmpb-data";
phases = "unpackPhase installPhase";
src = libsmi.src;
installPhase = ''
mkdir -p $out/share/snmpb/{mibs,pibs}
shopt -s globstar
for foo in mibs pibs; do
for node in $foo/**/*; do
[[ -f $node ]] && install -m444 $node $out/share/snmpb/$foo/
done
done
rm $out/share/snmpb/*/Makefile*
'';
passthru = {
proFile = "${finalAttrs.pname}.pro";
makeFile = "makefile.${finalAttrs.pname}";
smipath = "${finalAttrs.passthru.libsmi-data}/share/snmpb/mibs;${finalAttrs.passthru.libsmi-data}/share/snmpb/pibs";
libsmi = args.libsmi.overrideAttrs (
final: prev: {
#preConfigure = (prev.preConfigure or "") + "\n" + ''
# appendToVar configureFlags --prefix=$out/ --disable-yang --with-pathseparator=';' --with-dirseparator='/'
#'';
configureFlags = (prev.configureFlags or [ ]) ++ [
"--with-pathseparator=;"
"--with-smipath=${finalAttrs.passthru.smipath}"
];
env.NIX_DEBUG = "2";
pname = prev.pname + "-for-snmpb";
}
);
libsmi-data = stdenv.mkDerivation {
name = "libsmi-snmpb-data";
phases = "unpackPhase installPhase";
src = libsmi.src;
installPhase = ''
mkdir -p $out/share/snmpb/{mibs,pibs}
shopt -s globstar
for foo in mibs pibs; do
for node in $foo/**/*; do
[[ -f $node ]] && install -m444 $node $out/share/snmpb/$foo/
done
done
rm $out/share/snmpb/*/Makefile*
'';
};
};
};
src = fetchgit {
url = "https://git.code.sf.net/p/snmpb/code";
rev = "a092855bfd201778f87be578b91aeb062726e329";
hash = "sha256-nlS1pqv2ERZGkk0SJ8ByXqBHHho1GTSq/oxrXL2tytM=";
};
src = fetchgit {
url = "https://git.code.sf.net/p/snmpb/code";
rev = "a092855bfd201778f87be578b91aeb062726e329";
hash = "sha256-nlS1pqv2ERZGkk0SJ8ByXqBHHho1GTSq/oxrXL2tytM=";
};
patches = [ ./unvendor.patch ];
patches = [ ./unvendor.patch ];
buildInputs = [
qwt
qtbase
libtomcrypt
libsmi
];
buildInputs = [
qwt
qtbase
libtomcrypt
libsmi
];
nativeBuildInputs = [
wrapQtAppsHook
qmake
breakpointHook
];
#setSourceRoot = "sourceRoot=$(echo */app)";
nativeBuildInputs = [
wrapQtAppsHook
qmake
breakpointHook
];
#NIX_DEBUG="7";
#installFlags = "INSTALL_PREFIX=$(out) NO_ROOT=1";
installPhase = ''
popd
install -Dm 555 -s app/snmpb $out/bin/snmpb
#mkdir -p $out/share/snmpb/{mibs,pibs}
#for foo in mibs pibs; do
# for file in ${libsmi}/share/$foo/*; do
# ln -s $file $out/share/snmpb/$foo/
# done
#done
install -Dm 444 app/snmpb.desktop $out/share/applications
install -Dm 444 app/snmpb.xml $out/share/mime/packages
install -Dm 444 app/images/snmpb.png $out/share/icons/hicolor/128x128/apps
install -Dm 444 app/images/snmpb.png $out/share/pixmaps
install -Dm 444 app/images/snmpb.svg $out/share/icons/hicolor/scalable/apps
'';
postPatch = ''
rm -rf libsmi libtomcrypt qwt #ensures un-vendoring worked correctly
#smipath_parts=(${libsmi}/share/{mibs,pibs}/*)
#smipath=$(IFS=";" ; echo "''${smipath_parts[*]}")
substituteInPlace app/preferences.cpp --subst-var smipath
substituteInPlace app/*.pro \
--subst-var libs \
--subst-var include
pushd app
'';
env = {
include = "${qwt.dev}/include ${libsmi}/include ${libtomcrypt}/include";
libs = "${qwt}/lib/libqwt.so ${libsmi}/lib/libsmi.so ${libtomcrypt}/lib/libtomcrypt.so -lqwt -lsmi -ltomcrypt";
inherit (finalAttrs.passthru) smipath;
};
#setSourceRoot = "sourceRoot=$(echo */app)";
preConfigure = ''
qmakeFlags+=( "${finalAttrs.passthru.proFile}" "-o" "${finalAttrs.passthru.makeFile}" )
'';
makefile = finalAttrs.passthru.makeFile;
#NIX_DEBUG="7";
#installFlags = "INSTALL_PREFIX=$(out) NO_ROOT=1";
installPhase = ''
popd
install -Dm 555 -s app/snmpb $out/bin/snmpb
#mkdir -p $out/share/snmpb/{mibs,pibs}
#for foo in mibs pibs; do
# for file in ${libsmi}/share/$foo/*; do
# ln -s $file $out/share/snmpb/$foo/
# done
#done
install -Dm 444 app/snmpb.desktop $out/share/applications
install -Dm 444 app/snmpb.xml $out/share/mime/packages
install -Dm 444 app/images/snmpb.png $out/share/icons/hicolor/128x128/apps
install -Dm 444 app/images/snmpb.png $out/share/pixmaps
install -Dm 444 app/images/snmpb.svg $out/share/icons/hicolor/scalable/apps
'';
postPatch = ''
rm -rf libsmi libtomcrypt qwt #ensures un-vendoring worked correctly
#smipath_parts=(${libsmi}/share/{mibs,pibs}/*)
#smipath=$(IFS=";" ; echo "''${smipath_parts[*]}")
substituteInPlace app/preferences.cpp --subst-var smipath
substituteInPlace app/*.pro \
--subst-var libs \
--subst-var include
pushd app
'';
env = {
include = "${qwt.dev}/include ${libsmi}/include ${libtomcrypt}/include";
libs = "${qwt}/lib/libqwt.so ${libsmi}/lib/libsmi.so ${libtomcrypt}/lib/libtomcrypt.so -lqwt -lsmi -ltomcrypt";
inherit (finalAttrs.passthru) smipath;
};
meta = {
description = "GUI SNMP browser and MIB editor wrtten with Qt";
};
})
preConfigure = ''
qmakeFlags+=( "${finalAttrs.passthru.proFile}" "-o" "${finalAttrs.passthru.makeFile}" )
'';
makefile = finalAttrs.passthru.makeFile;
meta = {
description = "GUI SNMP browser and MIB editor wrtten with Qt";
};
}
)

27
packages/z3/default.nix Normal file
View File

@@ -0,0 +1,27 @@
{
stdenv,
cmake,
gnumake,
python3,
fetchFromGitHub,
}:
stdenv.mkDerivation rec {
pname = "z3";
version = "4.13.2";
nativeBuildInputs = [
cmake
gnumake
python3
];
patches = [ ./pkg-config-fix.patch ];
src = fetchFromGitHub {
owner = "Z3Prover";
repo = "z3";
rev = "z3-${version}";
hash = "sha256-9OpiMhO+75aHo3Nf7qcjC0QBXxxcvT8t7Mqc8bnjZoM=";
};
# CMAKE_ARGS = [ "-DCMAKE_BUILD_TYPE=Release" ];
}

View File

@@ -0,0 +1,22 @@
diff --git a/z3.pc.cmake.in b/z3.pc.cmake.in
index 436dd6208..4aa515b4a 100644
--- a/z3.pc.cmake.in
+++ b/z3.pc.cmake.in
@@ -1,13 +1,12 @@
prefix=@CMAKE_INSTALL_PREFIX@
exec_prefix=@CMAKE_INSTALL_PREFIX@
-libdir=${exec_prefix}/@CMAKE_INSTALL_LIBDIR@
-sharedlibdir=${exec_prefix}/@CMAKE_INSTALL_LIBDIR@
-includedir=${prefix}/@CMAKE_INSTALL_INCLUDEDIR@
+libdir=@CMAKE_INSTALL_FULL_LIBDIR@
+includedir=@CMAKE_INSTALL_FULL_INCLUDEDIR@
Name: z3
Description: The Z3 Theorem Prover
Version: @Z3_VERSION@
Requires:
-Libs: -L${libdir} -L${sharedlibdir} -lz3
+Libs: -L${libdir} -lz3
Cflags: -I${includedir}

41
scripts/dns/default.nix Normal file
View File

@@ -0,0 +1,41 @@
{
pkgs,
config,
lib,
...
}:
let
pythEscape =
x:
builtins.replaceStrings
[
''"''
"\n"
''\''
]
[
''\"''
''\n''
''\\''
]
x;
pythonScript =
builtins.replaceStrings
[
"@sops@"
"@dns_secrets_file@"
"@data@"
]
(map pythEscape [
(lib.getExe config.vacu.wrappedSops)
(builtins.toString ../../secrets/misc/cloudns.json)
(builtins.toJSON config.vacu.dns)
])
(builtins.readFile ./script.py);
in
pkgs.writers.writePython3Bin "dns-update" {
libraries = with pkgs.python3Packages; [
httpx
dnspython
];
} pythonScript

44
scripts/dns/script.py Normal file
View File

@@ -0,0 +1,44 @@
# flake8: noqa
import os
import subprocess
import json
from pprint import pp
import httpx
import dns.zone
# todo: dnspython to read builtins.toString vacuconfig.x86_64-linux.vacu.dns."jean-luc.org"
SOPS_BIN = "@sops@"
DNS_SECRETS_FILE = "@dns_secrets_file@"
data_str = "@data@"
DATA = json.loads(data_str)
secrets_json = subprocess.check_output([SOPS_BIN, "-d", DNS_SECRETS_FILE])
secrets = json.loads(secrets_json)
AUTH_ID = secrets["auth_id"]
AUTH_PASSWORD = secrets["auth_password"]
BASE_URL = "https://api.cloudns.net"
def req(path, **kwargs):
auth_params = {
"auth-id": AUTH_ID,
"auth-password": AUTH_PASSWORD,
}
params = { k.replace("_","-"): v for k, v in kwargs.items() }
return httpx.get(BASE_URL + path, params={**auth_params, **params}).json()
for name, zone_str in DATA.items():
zone = dns.zone.from_text(zone_str, origin=name)
pp(zone)
for name in zone:
node = zone.find_node(name)
pp(node)
for smth in node:
pp(smth)
# res = req("/dns/records.json", domain_name = "jean-luc.org", rows_per_page = 100)
#records = [x for x in res.values()]
# pp(res.get("status"))

View File

@@ -0,0 +1,60 @@
{
config,
writers,
curl,
lib,
...
}:
writers.writeBashBin "update-git-keys" ''
set -xev
domain="$1"
api_key="$(${lib.getExe config.vacu.wrappedSops} --extract '["'$domain'"]' -d ${../secrets/misc/git-keys.json})"
if [ $domain = github.com ]; then
url_base="https://api.github.com"
elif [ $domain = gitlab.com ]; then
url_base="https://$domain/api/v4"
else
url_base="https://$domain/api/v1"
fi
url_keys="$url_base/user/keys"
if [ $domain = "git.uninsane.org" ]; then
authorization_name="token"
else
authorization_name="Bearer"
fi
curl_common=( \
${lib.getExe curl} \
--fail \
--header "Authorization: $authorization_name $api_key" \
--header "Content-Type: application/json" \
)
if [ $domain = "github.com" ]; then
curl_common+=(\
--header "Accept: application/vnd.github+json" \
--header "X-GitHub-Api-Version: 2022-11-28" \
)
fi
# declare -p curl_common
echo GET "$url_keys"
resp="$("''${curl_common[@]}" "$url_keys")"
for url in $(echo "$resp" | jq .[].url -r); do
echo DELETE "$url"
"''${curl_common[@]}" "$url" -X DELETE
done
new_keys=(${
lib.escapeShellArgs (
lib.mapAttrsToList (
label: sshKey:
builtins.toJSON {
key = sshKey;
title = label;
}
) config.vacu.ssh.authorizedKeys
)
})
for keydata in "''${new_keys[@]}"; do
echo POST "$api_keys"
"''${curl_common[@]}" "$url_keys" -X POST --data "$keydata"
done
''

View File

@@ -8,113 +8,95 @@ sops:
azure_kv: []
hc_vault: []
age:
- recipient: age1y4zp4ddq6xyffd8fgmn2jkl78qfh4m94gcls2cu6vvjnwwznx5uqywjekm
- recipient: age1hkve3khk7fthyrwxjqdf4r37lrqpmnkz6mke7psuphvu2ykynqaq9g6ja5
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBZREpDaXVwSjBPZEtaUFU1
d1FTYnV1STlUdW5oeis4RStVckcvUFhPcndRCnNUdndTenhxN1M1STNlZmtqcWtI
amkxZitGZ2p1ZlNTRFVaYkNvWWdnRkUKLS0tIExLYm5PYVI4aFViaER2L1dUOGMy
d05BTDlqanFMQ1hjazRLUUVlaXpHL2cK+kXvv9khiwYlBK+lmqgYmHNNjMXHU5FZ
x5dpXndIiTRJ0cGtEgK78efbQmVNsHAae2X0E0IxbvrSe26S5PIbMQ==
-----END AGE ENCRYPTED FILE-----
- recipient: age1g9sh8u6s344569d3cg8h30g9h7thld5pexcwzc4549jc84jvceqqjt9cfh
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBONXlpMm5KTmZuKysybU0z
OUJCMmdrZ0V4amI4NTNtOEFqSXVtbW92cjFVCmlCZGF4bXMycXhJS3h6OWVpV000
SjZuQUFxelVpT3BXOVh5eU1vYnNKMjAKLS0tIG1KYjZJU1dMd1Y3bmxWaDhOSEJn
SUp1akQ2bUU0VmQvVkhheXZ4Zk5jWVkKqJ12/g0H8l6WwpiHxA0K3g3Ry4dpPb/h
2m84IYzpQA28BRCSHeIEeH1hQ1jU33/625XlNE1iJncPqu9YH5mXug==
-----END AGE ENCRYPTED FILE-----
- recipient: age1t5s3txyj403rfecdhq5q2z3cnavy6m543gzyhkl2nu5t8fz0zctqtvm2tj
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBLM3NCcGVPTS9hWHQvMCsv
RlJ5M0tVQWZIUm1tWSt2NlFVRGtHaTN1Rmd3CndVUHpEcU15S2lmbHpIY0h6WW1B
aEpRZVgzN0puRmlMNWNQNW94TXh6UUkKLS0tIEVXSVVVL2JaMGRFcldoVnZ1TFZz
bzJ3UGl1aGpsa0FGSVkzeGRHZDJWdmMKZgg4UtokzNDBuVZYoyYirTI1NEC3QGmm
ilOukMvpTZFYtKbwWVOuB8kyeudlkupavzlnHYAGBbpMVccpPeZHAw==
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBvNDFQQ3lMbGtBVjdBR0t2
MjJvcmpjQmtYR1VkSVYzTzJFZDZibmFKc1dNCkZpWUsvcEM2MnA2OWdOdXVsZzJi
VjFDOVNjdkVIZDgwWE5pQmpKWkxSb3MKLS0tIDlSbXZFY1R0dkl3NHdvSTlWYTZ6
bDV6UGVHd2RVKzVycHJUWllTMk1HU2MKkDag+K62PydC3jcvLaIxy0vOuANbA65P
hzaTNzv8iotafjFDYLWim7PLnxv+IeywKoL+Pnn4o3+e0617omx1mA==
-----END AGE ENCRYPTED FILE-----
- recipient: age1dzdf4rgep3ctk3dnrmrqtdgrchaa8nszfc4dp29gqwsst3z6jyrq57vfsj
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBOZ0tyczJoVzZxUmhIZG14
WDZjSlM0Q2F6VE9Yb1hRV0d5dGVoVmErVkJFCi9HbXdxZE9NZ0pLaFo1Nlk5QjRV
TSsrMlFqV2Z0OVlWVjRnYXpyTlNWdUUKLS0tIGZ5M2ZEWFR0NDNQUFQxMW1tTXlP
dDRaYnFZajR2S3ZoZ1FFWURYVFVpSFkK8YuczSfs+j3dL1OT4sr2/kfdAxPRstJj
SeDlvg4C0e2wKrqj0QwjN5oz8t21ELerXska7yZ3cod5gaQcFxB44w==
-----END AGE ENCRYPTED FILE-----
- recipient: age197a33mlf5294amjx59hycctu6wm4l3cu3w7n9rv3fs9340ql64rqjzpr7s
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBBNWlKeHh6UjNIRTAycEJ1
UVhJMi9CUVBsVld3YlBEYjVwaWE0T2V0cFJzCnpEb2ZxNkNwMDBDQ3JsQXVjY1lS
eFhqSkcvenkvOHNOclI3dkc5NytmQjAKLS0tIHkrc3ZEQjhJVVZlZWVJMVE0b0x5
QkxVMkhOK2hUS0lQVGlXYXUrVm1LVFkKyFIvkGHeykZBib8gNln1mEHtU5+Xr9rC
RpphkvAU9AA4J5/LXQs3To/WzTg9gt2fSxtrwk9TLheheRfUcHDuRQ==
-----END AGE ENCRYPTED FILE-----
- recipient: age1sqj8z3feqm2dk3gj8mxpfn5dpqnsmus862e8ayd0d4cdresqffdswcf9ru
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB6aENxNUpXUUxTcEZobkpW
SFo1UWlUSXRWbzF2bWp6WU9Idi93OWQvdGl3Ck1rdlNYZFR5dThKa3NaVFU4NWY4
dTdUNUdEQ1hkWkRsT0dNbVVqMytnTXcKLS0tIExXZlgydnhXTktyeDNrZmg0RFlt
QXAzNGk3MmRCSng2SlN5bGdiSTlJRTQKXy5hTxS47WVjw1ILaaNfMaW7YMIS3FGP
hvYeGGL2WHstUapyYb/Rgn46KJgk1gfDchYyHq+06SkpZRaUzCBDUw==
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBnbWUrNTN0Y2lzSjR1ckc1
cW03WXZFVzBSUzdpUzVLMWJzRjhqaWRFODFBClJGSno0QUpQaGpVSzJ0Y3h5eXFj
aGpoNGIycG80NkxhWEFGeU9IMk1tWFEKLS0tIDI3Q3lHNGI1VWJBcFZDRDBqNGpD
RDFNajdSSWQ1ZWNNcXl0T3lLcm1YUWMKm7w5OXFeuk7Sby68ODrk9EC8SbvCTxoO
oQueOepqeeh4wip3SQpHACvtUp4s85M6ZXE96uYioRlzy3zg39tIpQ==
-----END AGE ENCRYPTED FILE-----
- recipient: age1rz75dqzfd6gulwh270ukmt5amcau6j8dpxgzx8fm6u8sjkyx9usq69y4s2
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBUYWl1NUQzMElhbFBrbVBu
eURzOGFJSW85dFMzLzR4M3UvOVhQUGYvS0ZRCm1qYXJTUnpUcUVWUTFtRWQ2OHBO
UVg2UC9OSDJkL21vV3VNV0l1Z3ZHcHcKLS0tIDhVaGpFZ1djSnFaRnVKckxtQU0z
YlAyNGxsYno2U1NIMDVtVXJwcFA0ZWsKdNW5iANSWOGdSRYeBf/+/gtk7b+IN/ir
lo1HtaIT1a5tA28JfAo6ixIKdF5nnSIunM6Z0JlF9zKuJbBOmdVbHw==
-----END AGE ENCRYPTED FILE-----
- recipient: age148huz6rc3q9xx5t873ncx75sja2sazlescwspxl7lsmxsqkz0apsy8cldp
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBIWDd5Yk1pNGZ0UHRrc3lu
WWlPZTd5bFIvNVBqTWplR3NzdS8rQ0gyZVdVCkUvMEg5eWxCWHNyYTcvMFd6ek9y
Z0RudTRHanlTTVhYZDBuMkpsYTcwWjAKLS0tIGtDemJabDRVakJxMUdVUWQ2VjIv
NTBabFVLNENzWlNoUmZSUXU2eEJtdEEKuOXBlsIBsgjQvRZ4fKdoLfs1gqZYa4og
9o/mo+ciXYU3xPPOhnd/OTar/8pBpCBBCO0Ag+1Me/dVYbA0s8Jvvw==
-----END AGE ENCRYPTED FILE-----
- recipient: age1ck6lhd8thjcrdcnkn2epc8npztg0sfswahunjkwcf57rr0xaevys8fh0x6
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBCUnNZSEtpb0JVOTVjazFB
NHdXSnVxRm4vaXN6VE5leGU1Z1JGOHFEUUNVCnNwdUxweTVlanR2ODdvTzlDWkZR
NWVsY0k3WmFOWktsUVJGT1p6QUlKbGsKLS0tIEtnRVdxeWVYd29XZHVQWmZCNnhE
OElkbHNtUG1ncXdQWEpOcDNMeUg1d0EKF9OjITJDrkfZA2wI6Gm+0+MTDw4OPkQt
SDbNe5Gllo8BC1jTRM3H+uxsQ5L0TRrwnrSxNYjNdDIRHMrIxi3qcg==
-----END AGE ENCRYPTED FILE-----
- recipient: age13j6l33g0ghk4vezn0qwfal2qmcgqwkv89ejwezpe3n47mw8yxyuslj6y7d
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBqVk12WUxKdWdDVWRCU1dk
VkhNZWhNeWJ6OWJJaWdXNFZwRlZMT0lOTFdJClRyYkQvank0cGlZSzJGaE1LVVpO
VURjMnBIY3VvMkVnbzlJVGF0dU1FR2MKLS0tIHZlV0U4azN4aEVRU1YzWDN6U3Nz
YlIzbFBDd1pqMTVQa0diYnZjRmRRa2MKcPAvAB0B/zNj+mcavMkJdksWl8o1j8oQ
gGG8xdIEPT9wjfbL75IvHOy/7TKJR0uVomD8IB4QuVi1MxJh6jNJQw==
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBsMUVLVWpHaksvZkJIb0U4
RnVTZ0k0L0VlMjFNNFg4RVZjTmk1OHEwbGpnCkIxTXN5aWMwTlZEWERYRXV5dHEx
UVFVVEczRFhWRDJPN3g0QVh2NXlZUjAKLS0tIGNRbkk3R1RYVCs2Y2x4UmZhTXdx
UVUrQStXTU9yUWJ0SnlIbDBIRUdSb00K9oPKVn1RzK0DVtaeXnfURea9k1lNzpor
3ex6hSyrfzNazFlInCuptIFIpf5o1eeiiV2PL85w9wvpMh4MEG7peg==
-----END AGE ENCRYPTED FILE-----
- recipient: age13x0f3glnz4jvqty2v92cxrrnjcna6ed4qegrhulw9jjy08zuy3aqzvrfc6
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBpbmxpNlZvV2JWYmRJS3lq
Um5GVDQ0ampMTDdzZHB1RFFqZ012bFZMd3g4CjdoMzdOUXhtSEF4Tjk1UTJlNGNG
TzAwSDAvK3VCL3ZheW1HOHFCclU0OEkKLS0tIDY5anhYeTQ5RGxNUlZNRXg5Rm1o
QVk5dm5RaWpocUZrWk02Slg3N2lONjAKxWKAmAHt9x2T/9bh2mnQIF03ufffO9wF
79jffMh/3GyX5Pk0IbjMWwOn7ahQWOEgD58C1Lja2wpixLdwb0wgfA==
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSA1MHUxcU9tR3JKSjk5TGRm
c2I3S0lrV1RJZHFkN1JyNHlqc2hXbGtPVlVzCk9pMmVRdC92bld6SW0rNFVyRmJs
QmVOMXRrb3FvVUNUYnVuczg5MklEL1kKLS0tIEE2YkRmeWFONVpDTk02S3kwSWNI
Ty9PdGYxUnRNSUIxN21RWWJUQnVqWjAKp1KybOk5/5xHHggBwE7zyuOw17GwxPCw
UR2R5wuc0d1Uyb/z/QvRI4lbpjAhjb749JgLE2IYTYLfPsJv59K8BA==
-----END AGE ENCRYPTED FILE-----
- recipient: age1hkve3khk7fthyrwxjqdf4r37lrqpmnkz6mke7psuphvu2ykynqaq9g6ja5
- recipient: age13j6l33g0ghk4vezn0qwfal2qmcgqwkv89ejwezpe3n47mw8yxyuslj6y7d
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBhcUJUTFRrZmxiN1MrZkZB
V2FjSlM5ZUxyUFZMKzRoYzY1M0plcmhjckJ3CjBhY0VRT2VMRUR2N01YZWZVRkJk
VEdqSTNvLzNBOElZVVUxZ0VBekx6RnMKLS0tIHNtVlA4V1R2bkFBaVJMYkk3eUNm
TjhQY0VoNU91Zi96VzZGaitsWHptT0UKZ3Vx/iqilkHrFkAbaSeJZNmSOzXvMDX6
HhcXrrq+sVjnq0XhOqWVY72h8Hp3d0JWA9VOxNQRyM9hdVENXur8YA==
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB2c2cyOWh3bEtBMUF6a3hx
UjVIYkN5cE1ZcWNZM1V3Y3lhR05JYUt4Q3djCk9XNWF1dnhveVlLNWxJSVcxcVRK
V2d2aWx5ZXdrYUw0TFN3VGVZTE5RTTAKLS0tIDNnWm5nbDZUbmh3QTBCWXp6aUE0
ZFhoeXRTOEhDT2NpOXM2L3NCdVNEQmMKBp4e23mcqrJdlcqbf6mUjitYq7MxkeoX
jX8LQTucw9dhLu/SCxymRxg9/Q2+PfhUvDR2L51tdlbr77dRhic3/A==
-----END AGE ENCRYPTED FILE-----
- recipient: age1vla9w33lsp03s46p9p6gc2mvr844vthdqhc2hzau2ph6h60gmyqqh9sf57
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBoeWltSkV6aGJ1WkJOVTBp
Q24wMEFuWlVQYXMrKzRrSHN2THB3TWtYQ0VvCldHUmlpUGdNTlp4QkluZjRzK0J3
U0ZGYWM2eFZyZHhuT2dWSnBJdzA0dmMKLS0tIHg0citENmY1QkpXNURzY2x4QkZM
bG9DUTFkd2t3YXFXVElKK3JsK216Rm8KGvXixYViOUwrVarBMZeUI5HlCBtoL5bp
7uZ9JFKQMh9EtiUk+Pr2xr4r9Mah0Gk3AmmVKWvaQaC/bkEIhe30Eg==
-----END AGE ENCRYPTED FILE-----
- recipient: age1jy8mxcndkw6zd6q99tjgz3gsynn78x2lwtrff85u6ud9g9y9z5mspvhufl
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBnYmhVb0FsdUc5RjdPWnA5
ZmpaMi9Rek5WM1AvSVl3Nk1maG1YanJaS0RzCjM3VEJKM3dVclZxK2FSMENKTUUz
d0dleUU2Rk5namdUdFl4ZjNSM05xdnMKLS0tIHRzYldRM0I4MytMcGFMUnZ3QXA0
MGtKcDMyejNFNktCL2I4RUI3Qkk1TWMKsxjqBw5J91f3T9TDHNAKFI2cTT4i7zJw
N33KbrskOaOXjCsoENnqdRl9Y7v/JbOh5YQ2/oPwZEfuwgHG9lcXqw==
-----END AGE ENCRYPTED FILE-----
- recipient: age148huz6rc3q9xx5t873ncx75sja2sazlescwspxl7lsmxsqkz0apsy8cldp
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBWdWRCdnNybjdzSFpacjNj
eFNJNjBzYmpsRkw4czN2aWJzSnBDeFYweDM4CmZCcnZCTEJQTGtoSlo3VW45T0ZJ
bmpUMHhFMy9mSUxaTWVCcFBnQlAramsKLS0tIGV3eHcxRlJZc3BxQUU3TUhsRVAr
VXdheGpVRFF2UFBKQTF0OFMrVzdYcjQKaEs1irVwO0OoXbBhYd1AgCCPPF3sFH3a
go3jAHOCnwkYQMVRd24FGZx28XuEgeXQALk7JqEEy5eCS6nKDEVqcg==
-----END AGE ENCRYPTED FILE-----
- recipient: age197a33mlf5294amjx59hycctu6wm4l3cu3w7n9rv3fs9340ql64rqjzpr7s
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBHcWZxa3NHR0Z4TmlNNHVU
aFNvN2tycVd2THhFMGtMckhGOXBuZXNMSkFFCm1VR1ZwUHdabFdBWmUxUXVxTVR5
eFVvakFDZUV2WHByU2pRU3hrWXVaMGcKLS0tIHRjbElYOU8xaW1lVFlrL0YwMDlQ
MEwvd1RQd1hlNVNZL3VveUkydVNjVE0KFsyjr38WdXu4R0038Dum0VeVw+LNcI6q
4R0ft0KsfLLmPgoNIdK5Dq5hUxyGVe8Ej/9KaN0UrqIRsLHCHimYyQ==
-----END AGE ENCRYPTED FILE-----
- recipient: age1sqj8z3feqm2dk3gj8mxpfn5dpqnsmus862e8ayd0d4cdresqffdswcf9ru
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB4QW9yVk9zN2RrZkpTWXZU
U080M1pDdzV1bDFSR2UrY0o2dnoyYlpNZXc0CmJCSE84L1ZRdUVZc21GbWc3cG9t
NHRGQUFVS3U1TjFVYWl1Q1FyODY3UjgKLS0tIGhrY1dMa251R1hCc0F5eDhtWnc2
bXpqNkVobzgwMHJIdHBFZ0xDZ2RzcmcK0m4awMUrdwYvXO14L1hvhcaGgLOW3FCq
UU1Vc/vX32Lsu1BN4aXlTZ1jHD6R6CnV5TbUTcM/jxFRKoRzDwdJig==
-----END AGE ENCRYPTED FILE-----
lastmodified: "2024-07-10T20:44:49Z"
mac: ENC[AES256_GCM,data:tSTKCP7HUUCSCrbeiLutPghjfbL9TsxuCmbARUqwQBH8pyeOsyFHyPCqmqjCDSu2ha0QTldNGM9baiIQa/05DV5KNmFfVuoWy6dd4/3L5yNd3FPkzR2SvBua1g09YZpC1G2IaGrOcqBEOY9baILeBGgXfxRtcpMVAR2C3bOqJyQ=,iv:4phBdZ/4u5DAbUn4Z7pdrJym+iG9oxZSsIPZqoDEqco=,tag:RJn0416yl+0FV9bTu5tA5w==,type:str]

53
secrets/misc/cloudns.json Normal file
View File

@@ -0,0 +1,53 @@
{
"auth_password": "ENC[AES256_GCM,data:UD8l+CrofmN9g439uTOtCyP5378VX+f856dxuFDTzfCa8B+7,iv:6hgG+py3EC4cMLkhG72O5HJfbQF5Q+APq6wBsMQVRjw=,tag:KA4AupZKFdHEBzEBnd3/1A==,type:str]",
"auth_id": "ENC[AES256_GCM,data:4cBXpVc=,iv:WPh6+xp02CMBohmxWu6UdNA3KMRSghbSQYuU0lZyUMo=,tag:+zU0EBEwLgqYC0NmW31Qtw==,type:str]",
"sops": {
"kms": null,
"gcp_kms": null,
"azure_kv": null,
"hc_vault": null,
"age": [
{
"recipient": "age1dzdf4rgep3ctk3dnrmrqtdgrchaa8nszfc4dp29gqwsst3z6jyrq57vfsj",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB3YW9haUtvVVRkZWVqa1Zv\nOERucllIenc3VFJkMzAvM1paTWxNaVA4MlhRCmZVNGpvdmhrUnJDYTMyWExNVVNW\nQWw2MDBPUnozTWpzTERiaExYVkJUd0kKLS0tIEFPRUhjZVdBTXZQdFFUQ0NnYU5P\nYlkvaUgzQjVORTNvTDFKYXJJYW1pTGMKW2rUNzNWsvQ9vzf+jwSBOC8OjVL30HDZ\nK8QC30Z4PUtKTk5HA7KcFfGVT8UbJc6Z4IRm6dIV6lczmctZiuAXLQ==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age1rz75dqzfd6gulwh270ukmt5amcau6j8dpxgzx8fm6u8sjkyx9usq69y4s2",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBMdGxOMkNFcnRWd2EzaGVV\nNGdxTDUzM1FnY21tUUtJOEhaM0RFU2ZZbXc0CkIzVXBNY0Z4dmlVRnpHZGt6dzY4\ncW80b0lCdCtJMnQ2aXJyclpiT1BlWG8KLS0tIE4vV2gwZjBVSmc0Y3ExZUdXQnJL\nMU9EOWNNRDJualAvUjNOWlZCMjdHSU0K33nP6rM7k9er+8gC2cozXF3M7WNAPb3y\ny5ecWeGnIJe1Q3BwpqXUmxWswE95VYq6g4RCJ2TbHIJWgK6HLJoamg==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age13x0f3glnz4jvqty2v92cxrrnjcna6ed4qegrhulw9jjy08zuy3aqzvrfc6",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBzM0kyMHZ2UEpaYzMzMFRo\nV3IvYVI0RTVUM29pSnhYUFBpUlVnM3BUcEZBClpCL1c1cmFaRzZDU2tQY2hJQzNx\nb2ZvdTRBMVNTS01XdTJiYnljMzhiUFkKLS0tIGFuR05CYTZhbVdZMERCVUcrRTFO\nQWREQW9DU3pmOFRJczVBdTA0VFdwZ0UKuhijkZjfHrOrQ28WF0lsrh1YYcDjohJF\nHimoJrsMFf21bsWMPGsRXvvQWouMhhzDtp3ZzaR/jhwzqnNp6I2gWw==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age13j6l33g0ghk4vezn0qwfal2qmcgqwkv89ejwezpe3n47mw8yxyuslj6y7d",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBHcHlmTVJ1d3ZRc09WMU5p\nbmd4TzZNVisyWm1PZFBmMXpBcmd6N3ZmL0JBCnBqZzZCNVFObHpZZzd3cXBuaEVR\nZjJCdTRLalhBTnpEN21NYzRQUnFrbjgKLS0tIDJIVDlFZzJuK1pnYklaZnRWOEgz\nNkxLNSsxbzR4cUo0TVVsajNLeXZvZEkKCqo8Hw+CoO+lpKXxI1+3Pkw6iNcaJlzU\n7HE78dhMH2C01Phn9BOFY3FATxo68wYxzLWUt90iGwtnxT1K509GGg==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age1vla9w33lsp03s46p9p6gc2mvr844vthdqhc2hzau2ph6h60gmyqqh9sf57",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBRWnlkYUI3ZFIxR1dBZzNi\nNDRGT2xIZFhyWCs3SHk5Q0toWmZUc3F3RTFVCnZtZUFzNDdOMnlQWVlYVjJnYlJN\nV2xXM3F4N3RVTzVFZE5Zb1BkcjI1cUUKLS0tIHdiQTJTQlpJQlNycElCamN5MGth\nWnNKMnlEQTExbis3dktsWDliaU9IelUK/fxqRPnRbD+KCvYMI4m5K17cLI2/xEbL\nbsGdj8E0TAtzqRL4iBOQfb6xJC5AqcmHEhvFnnxEouNUXMsw5/1Ggg==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age1jy8mxcndkw6zd6q99tjgz3gsynn78x2lwtrff85u6ud9g9y9z5mspvhufl",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB3Zi80ZHU0WnVjMlpycVov\nWE9UNldKRmdMR2xkNVNuQ0NPWHNzTUg4cEU0CmhjdGhEdG5GWkxKUUdRUzMzN0RL\nRHo1QkdSaDNxTy9RVDd5TGtpZUpaRmMKLS0tIG1TTFdrNC9MREd2K0NIdmNscjB5\nQlpGMVdmK2wvQnVxMXJkeTdYbXJtZ0EK12lVIHRp/GxD4F0oMsiOmy4RC5iJEkle\ngvTGPFJkiJJJe36vMx34WdKq++6fwma624E75S4P5qmiVIeadDihGw==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age148huz6rc3q9xx5t873ncx75sja2sazlescwspxl7lsmxsqkz0apsy8cldp",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBUYm5Ca0NId3AyRUwxRU1q\nR0NvSUk3YmJvOVRvbTVkVjZ0ZzVxaEFtcGpFCjg3V2ZhUk9RM09ZNVRGVEhUZHZ0\nekNid3NtUVZyTTlZSFU1QkQ0amtEcUkKLS0tIDlTdTBpdDE3VHkyVHhHekZDUEdP\nRUNpdm9ENHhCWCsxbk9aOVFmeFBwUzQKJzTxCMPaYYsmjoGyEbuimDWpq5Oq8oMx\n2LXkQHYdmBi090o4ocfkHiR1SS3w6XNI8IBcQK1flobXYejI9E5yKA==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age197a33mlf5294amjx59hycctu6wm4l3cu3w7n9rv3fs9340ql64rqjzpr7s",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSAvR21LYis4SXFxcE1PeXQ3\nelpxRTJ3Y2svRnc1ZTkvVk9lTUhFSmVneWc4CnJMT05ZQnBySDBuZ2lqcnc3eHlv\neWdKUi81aWlhY3pySzhoSjdwUlhMN0kKLS0tIDRWWFR5Q0oyZ09GdlF1a0JmeVdl\nOTV4TUhWdVBVRFhxQlB0ajFSS1FnNHcKMq1FSE3OecwHopvkShKQYSFQihzFkMrG\nFRpPqWcUzaXpib8f4YQrYmLJiihGCpfovv5+NHEQB8BMEu7UNY/emw==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age1sqj8z3feqm2dk3gj8mxpfn5dpqnsmus862e8ayd0d4cdresqffdswcf9ru",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB1YnJVMmpSNDlicUh6UEJR\nL1JUZVlxeUhmTGpUeXNtUmc2NmZGc3NObldVCitHOUgyOXFibnR3WUZRdjc3TExZ\nK0lxRUJCY3ozZExlNzRack5jTTR4aFkKLS0tIGVoOTRCNW5Yb2NVd09ZU0kzSlNV\nVWxuYjVCM3lvZHhQeU05R09WNWQwU2MKNM9VU6KE/0AUzww/qdMQoXMpZ9MT5rIK\nOvltRcVvQR1lZqiox4W1zYfw3JTlficQ31C+wSMHy4aBSlnik7hzxw==\n-----END AGE ENCRYPTED FILE-----\n"
}
],
"lastmodified": "2024-10-24T06:58:19Z",
"mac": "ENC[AES256_GCM,data:P5ipojcOVW0V/4J7Txj9v4RONAzqIIG71guYkqHZ/yJNrFIjVn+db3qLNbNmeKz73rbPdXYpZGM5dIwXiF9pzLAW+t3pYABGvnBT/l1cN1tYS4BCs+e6n0KqKho/Aust/QTDIuYkoAyRwD7HD/OXW8V5SJtiuaqAlX9gzDLILs8=,iv:oUxrQbPTgL/RfdGvw9rnx/mU4RklD2uet/3XRQH0pq4=,tag:wj3ehRASFcW1g6Yf8XxSKQ==,type:str]",
"pgp": null,
"unencrypted_suffix": "_unencrypted",
"version": "3.9.1"
}
}

View File

@@ -0,0 +1,54 @@
{
"git.uninsane.org": "ENC[AES256_GCM,data:g1oZA7s16sl6tBsUy+aAUChYBomgxht08dzghBakmJ/13YrM/Pf7WQ==,iv:v3CXUaLwIdEtg6ZWiCqqZ1JSkWOlnWnGSOzNVAx5gvs=,tag:jkQGgxRMBggokRNUdW2jLQ==,type:str]",
"gitlab.com": "ENC[AES256_GCM,data:A2+dsAgvVJsqgGOHcPsw7F5bSTg8H3icd+g=,iv:v9QVy7vP/XEHw0lHBjedvWFrsGvyDlAEF+yFL1voiQc=,tag:0kqgQOIn90MBjiNRHjiRrg==,type:str]",
"github.com": "ENC[AES256_GCM,data:fpY8KxwIYGvIWAHKH7cmwCO4j7fPx+625Buvhu4OdJIpcDXJrpjTsQ==,iv:4W2YvZ01XjzJUX3yXx9H+kxtylYRma4wA/YWL2W6kPc=,tag:WswVoBWgzjrpz9nPQfVV3w==,type:str]",
"sops": {
"kms": null,
"gcp_kms": null,
"azure_kv": null,
"hc_vault": null,
"age": [
{
"recipient": "age1dzdf4rgep3ctk3dnrmrqtdgrchaa8nszfc4dp29gqwsst3z6jyrq57vfsj",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB5VzNHZnJwVmdKNnN6Qjc4\na21FT0hTR29PSE9PR05uZjRuTHR2TWZVK1Q4CmQ0c3lXcW90eVhtVlk0Q1NheWRm\nUnBLS3p4RXVUZ0dneXM1dFNRLzVlUGcKLS0tIG5uWE1NdSswU0ZodW8rdEg5ZDZw\nQ3J4T3ZHcjc4YmpsYmVnS2w1VzRKOGsKE3QwbGADwS/pbnQrtmaZ7w2oVEBB4pPk\n+ZMYWwEF80FF9iCRnvb9qotKRPDE4bE64xgv+eAP/fuKSvENb0Umjw==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age1rz75dqzfd6gulwh270ukmt5amcau6j8dpxgzx8fm6u8sjkyx9usq69y4s2",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB3TlhYc2VieVZrdXQ5M01j\nYjNwMFJKSVQ3bkdxQTVYRmU1dHN2QUd0dDFNCjg2NnRLNVFYK3B0b1F0b0huLzMw\najFvL0E5S2ZuWWwydmxNZ2xmZFUxU2cKLS0tIEp2YzlqQmFwRysrb1N2WjVPbXRJ\nTkMvMkFRMlBMWjd4WjhKZy8vclFNRUUK62LABvyUbhlOrWP88CbCG9gTBrGPUNiZ\nz+/fheIYKQdvgZOWJsa/TsciaBPPdm+XF4Y+zc6Rzrd0qlZNZVSsXg==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age13x0f3glnz4jvqty2v92cxrrnjcna6ed4qegrhulw9jjy08zuy3aqzvrfc6",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBSUzFCaHMvUy9Wb0xDRU0z\nMzNXOGdPSmxjT0VBSFY1NzZoUGpJUHE1YVZrCk02cDRyd0FGOHlXZE9Md2J5djlE\nVE9PeHMyL25YSktlT0w1dk1mT1c5UWMKLS0tIHoyc2c5cEtOaWU2VFhtK2dUTW43\nelFYNG5XeFJscnlINFhLRWUrazcyRkkKql2yUeNuqA1yOAA7BsqSDTXw7tSc2Wt6\nD0ajblyUP+HxzvJILs0LiTruaiVw8LGYHV9a+oUuMV6UJGthf7w25Q==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age13j6l33g0ghk4vezn0qwfal2qmcgqwkv89ejwezpe3n47mw8yxyuslj6y7d",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBsOVE3VUR4aUd4QWtTck5S\nR1lmTlJRck5ncFNZcjJ3RkNPL1JWTWVyMW5NCnQ1dmIvUXV4U1ZaN3lLa01uYUdr\nU3d4dEg4QkNqTFYrdXlKRk1XdWtReWMKLS0tIEpuTUZVUnVGOGdobTdaNGJhaFpC\nWWRPYXBFYzYvakc0NnI1ODl6QzZ2K0EKlX4Xa2DyeasnuDVTQ0MjcnQ8suQZaAuw\nvu29LJOCtOx+EdjFiMXtNMR6jw1HWFeUvhoR6/EkPMHX52Ai9rBLwA==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age1vla9w33lsp03s46p9p6gc2mvr844vthdqhc2hzau2ph6h60gmyqqh9sf57",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBCV1prUUxCeWlLMm0rTHI5\neW40U1ZoRll5d0JCUm9LSnVBWmZWRnc0NGlZCjlqYUc4bXZ1OWYxQnNFWFl6MEM2\nZ20rKzEySTVMUlo0VUtBYUdqd2hETU0KLS0tIFpBN3BZTW9mc3lRbHBPUEN3SzVo\nRFRUOUtseGl6YWpFOVZ0Tk9tVGNwNzAKNKdHEE1XwW4aqc4Vdj8qc/yqtB6JUJcB\nB5mD80Nff6QJzVWCSSZAxe6c6UET5eFFfZW7h9lJeFn2NOSmuM2adA==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age1jy8mxcndkw6zd6q99tjgz3gsynn78x2lwtrff85u6ud9g9y9z5mspvhufl",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB3VDlVZXZvSHlWcDF5cDFQ\nUlF4TnAwV3BsbGkrNmgrdzdQTk93TE5mYWtvCkd2YzdaU2tQSk41SmN5N0dPRjlI\nNXVLWDNlQkkzb1Z4Y3AwZ3Q4Q3RzVjgKLS0tIDkzZEZIWDRKTlUvSXBkaUtHc3hp\nVUo4NitVSStOeE5vamJFTjNMdStFMzQKZKckoNsPO85FznhBAuH/9GGVzWyJjq/5\nF1WU+5PrqdvQ6cQWZ/AVGxhuxD0L7Uy7Rt1iheQ971ML+3L/iquD0w==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age148huz6rc3q9xx5t873ncx75sja2sazlescwspxl7lsmxsqkz0apsy8cldp",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBWejk3Wk56dWFKNnFqYk9m\nSTJEcHZxRkh5ZVZFMk5HcEo0YzRCYk5JYUJZCkEzRkJEZDBQOU5aeG55UDhuc0w0\nNFRlZXp3TnI5cVM4U3FiQitJREF6aTAKLS0tIGVucTNxRk9OQmd1cjdlZHBUa2ZV\najdXdEIzQWlWQmZkbnQzMzVPb0hCaGsKQvAUO3k8QFBWAki96WJum6jO1Yu2Uua4\nvJbDDCth5FhSIXdu5Gw1m0iiuSqcj+9huSC9zuX9w9vbqLxISmesFg==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age197a33mlf5294amjx59hycctu6wm4l3cu3w7n9rv3fs9340ql64rqjzpr7s",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSA3NndrQnZRbnAvUEhua2No\nRm5KL0NRRUhwbUd2ZXptL2dsK0xIK0xEQ0dvCklpWmEyWXptYmVnNksyY0NuSFR4\nWG1kbjlVTDJ3SzhCaEFad0pWeDVCS28KLS0tIHVDdmhiS0ZmMDYzTlhTb3BVcXR0\nS1ZVTGc3OHFZS3lZbXAzYTVCejFnRFEKITQHLZqOvAmoKjkQt8KOYWhTUE+DGy9r\nFdtHmTfv/4UKDpqv/WqkTIvi5AUWApWJ+5YCm2Fv0Y2sFXhBK3kF4Q==\n-----END AGE ENCRYPTED FILE-----\n"
},
{
"recipient": "age1sqj8z3feqm2dk3gj8mxpfn5dpqnsmus862e8ayd0d4cdresqffdswcf9ru",
"enc": "-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBPek9CVk5pQW1EUUhabW5E\nTWFjdFdlVVFnZlcvQWlOTk5YZTVTRWdMMmtRCkJwWjlWREdjRUhEL2R4bFRBQ3Aw\nZjdJMCtVZDErZE5wcnloR2lvVnJHSDgKLS0tIDAwajE2YTA4UFo1SmJEVUtpN2hX\nMkkzYjZOVDYvSlRGT3RJTzdySlJleXMKor4NR2gIkfvDi25eKrzLki+biWf3dVZS\niCSBxy+tpbtiO9fK8LPrz9jJp1tBism7VTIF6WBuj97GjMGHIOz43Q==\n-----END AGE ENCRYPTED FILE-----\n"
}
],
"lastmodified": "2024-10-24T05:55:24Z",
"mac": "ENC[AES256_GCM,data:ntQuFNOlw0CqRQO6hLOwocSyNs04KzlPlpr4k+Vxw5BOoRhDeLAvyrcrfduDw2vh9OUhHaNyc15j5J8s5akAVsf1DSfnK5HUbBB6Qp4W8YkCCAP+S8d6/iBniqlWsJeioVAX/mNXwUaFe7zZ2WDp1s/LebO2hSld1MHkW+uZGXQ=,iv:7pgK+ZqWEgWY01ugIzR5EuK4TljdFkrRvayN5AOh0Qs=,tag:zt1EaL86geu0ucHZR6WHIQ==,type:str]",
"pgp": null,
"unencrypted_suffix": "_unencrypted",
"version": "3.9.1"
}
}

2
sops Executable file
View File

@@ -0,0 +1,2 @@
#!/bin/sh
nix run "$(dirname "$0")#sops" -- "$@"

View File

@@ -1,7 +1,17 @@
{ pkgs, nodes, lib, ... }: let
{
pkgs,
nodes,
lib,
...
}:
let
certs = import ../deterministic-certs.nix { nixpkgs = pkgs; };
relayDomain = "relay.test.example.com";
rootCA = certs.selfSigned "liam-test" { ca = true; cert_signing_key = true; cn = "Liam test CA"; };
rootCA = certs.selfSigned "liam-test" {
ca = true;
cert_signing_key = true;
cn = "Liam test CA";
};
relayCert = certs.caSigned "liam-relay" rootCA {
ca = false;
signing_key = true;
@@ -20,7 +30,14 @@
testAgeSecretFile = pkgs.writeText "test-age-key" testAgeSecret;
sopsTestSecrets = {
"dovecot-passwd" = (lib.concatStringsSep "\n" (map (name: "${name}:{plain}${name}::::::") [ "shelvacu" "julie" ])) + "\nbackup:::::::";
"dovecot-passwd" =
(lib.concatStringsSep "\n" (
map (name: "${name}:{plain}${name}::::::") [
"shelvacu"
"julie"
]
))
+ "\nbackup:::::::";
dkim_key = ''
-----BEGIN PRIVATE KEY-----
MIICdwIBADANBgkqhkiG9w0BAQEFAASCAmEwggJdAgEAAoGBANn62hMdcFw4znAB
@@ -41,123 +58,156 @@
'';
relay_creds = "[${relayDomain}]:587 ${relayUser}:${relayPass}";
};
sopsTestSecretsYaml = pkgs.writeText "test-secrets-plain.json.yaml" (builtins.toJSON sopsTestSecrets);
sopsTestSecretsFolder = pkgs.runCommand "test-secrets-encrypted" {} ''
sopsTestSecretsYaml = pkgs.writeText "test-secrets-plain.json.yaml" (
builtins.toJSON sopsTestSecrets
);
sopsTestSecretsFolder = pkgs.runCommand "test-secrets-encrypted" { } ''
mkdir -p $out/liam
SOPS_AGE_KEY="${testAgeSecret}" ${pkgs.sops}/bin/sops --verbose -e --age "$(echo "${testAgeSecret}" | ${pkgs.age}/bin/age-keygen -y)" ${sopsTestSecretsYaml} --output-type yaml > $out/liam/main.yaml
'';
in {
in
{
name = "liam-receives-mail";
nodes.ns = { lib, nodes, ... }: let
liam_config = nodes.liam;
in {
networking.firewall.allowedUDPPorts = [ 53 ];
services.bind.enable = true;
services.bind.extraOptions = "empty-zones-enable no;";
services.bind.zones = [{
name = ".";
master = true;
file = pkgs.writeText "root.zone" ''
$TTL 3600
. IN SOA ns. fake-hostmaster.example.com. ( 1 1 1 1 1 )
. IN NS ns.
${relayDomain}. IN A ${nodes.relay.networking.primaryIPAddress}
${lib.concatMapStringsSep "\n"
(node: "${node.networking.hostName}. IN A ${node.networking.primaryIPAddress}")
(builtins.attrValues nodes)
nodes.ns =
{ lib, nodes, ... }:
let
liam_config = nodes.liam;
in
{
networking.firewall.allowedUDPPorts = [ 53 ];
services.bind.enable = true;
services.bind.extraOptions = "empty-zones-enable no;";
services.bind.zones = [
{
name = ".";
master = true;
file = pkgs.writeText "root.zone" ''
$TTL 3600
. IN SOA ns. fake-hostmaster.example.com. ( 1 1 1 1 1 )
. IN NS ns.
${relayDomain}. IN A ${nodes.relay.networking.primaryIPAddress}
${lib.concatMapStringsSep "\n" (
node: "${node.networking.hostName}. IN A ${node.networking.primaryIPAddress}"
) (builtins.attrValues nodes)}
${lib.concatMapStringsSep "\n" (d: ''
${d}. IN A ${nodes.liam.networking.primaryIPAddress}
${d}. IN MX 0 ${d}.
${d}. IN TXT ( "v=spf1 mx -all" ) ;
${liam_config.services.opendkim.selector}._domainkey.${d}. IN TXT ( "v=DKIM1; k=rsa; "
"p=MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDZ+toTHXBcOM5wAQirYejeCQ/F6zXswmG78q1HFaRpJDF90wvbBMmYBlemNgrPydkOoympAuO513m81RHZP5FrAKY+Cez0JeLfxt739a3XyAkMdaSLKbJqkCrGLoFBtfBLoBGc3pWot/p+FMKrHneOedWkbcGsLPHSUHjzhBKtQQIDAQAB" )
'') liam_config.vacu.liam.domains}
'';
}
${lib.concatMapStringsSep "\n"
(d: ''
${d}. IN A ${nodes.liam.networking.primaryIPAddress}
${d}. IN MX 0 ${d}.
${d}. IN TXT ( "v=spf1 mx -all" ) ;
${liam_config.services.opendkim.selector}._domainkey.${d}. IN TXT ( "v=DKIM1; k=rsa; "
"p=MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDZ+toTHXBcOM5wAQirYejeCQ/F6zXswmG78q1HFaRpJDF90wvbBMmYBlemNgrPydkOoympAuO513m81RHZP5FrAKY+Cez0JeLfxt739a3XyAkMdaSLKbJqkCrGLoFBtfBLoBGc3pWot/p+FMKrHneOedWkbcGsLPHSUHjzhBKtQQIDAQAB" )
'')
liam_config.vacu.liam.domains
}
'';
}];
};
nodes.relay = { lib, pkgs, config, ... }: let
mailpit = pkgs.mailpit;
dir = "/var/lib/mailpit";
in {
networking.firewall.enable = false;
users.groups.mailpit = {};
users.users.mailpit = {
isSystemUser = true;
home = dir;
createHome = true;
group = config.users.groups.mailpit.name;
];
};
systemd.services.mailpit = {
environment = {
MP_DATABASE = "${dir}/mailpit.db";
MP_SMTP_TLS_CERT = relayCert.certificatePath;
MP_SMTP_TLS_KEY = relayCert.privateKeyPath;
MP_SMTP_REQUIRE_STARTTLS = "true";
MP_SMTP_BIND_ADDR = "0.0.0.0:587";
MP_SMTP_AUTH_FILE = "${relayPassFile}";
MP_UI_BIND_ADDR = "0.0.0.0:8025";
nodes.relay =
{
lib,
pkgs,
config,
...
}:
let
mailpit = pkgs.mailpit;
dir = "/var/lib/mailpit";
in
{
networking.firewall.enable = false;
users.groups.mailpit = { };
users.users.mailpit = {
isSystemUser = true;
home = dir;
createHome = true;
group = config.users.groups.mailpit.name;
};
systemd.services.mailpit = {
environment = {
MP_DATABASE = "${dir}/mailpit.db";
MP_SMTP_TLS_CERT = relayCert.certificatePath;
MP_SMTP_TLS_KEY = relayCert.privateKeyPath;
MP_SMTP_REQUIRE_STARTTLS = "true";
MP_SMTP_BIND_ADDR = "0.0.0.0:587";
MP_SMTP_AUTH_FILE = "${relayPassFile}";
MP_UI_BIND_ADDR = "0.0.0.0:8025";
};
serviceConfig.ExecStart = "${mailpit}/bin/mailpit";
# serviceConfig.Restart = "always";
serviceConfig.User = config.users.users.mailpit.name;
serviceConfig.Group = config.users.groups.mailpit.name;
serviceConfig.AmbientCapabilities = [ "CAP_NET_BIND_SERVICE" ];
wantedBy = [ "multi-user.target" ];
};
serviceConfig.ExecStart = "${mailpit}/bin/mailpit";
# serviceConfig.Restart = "always";
serviceConfig.User = config.users.users.mailpit.name;
serviceConfig.Group = config.users.groups.mailpit.name;
serviceConfig.AmbientCapabilities = ["CAP_NET_BIND_SERVICE"];
wantedBy = [ "multi-user.target" ];
};
};
nodes.liam = { lib, ... }: {
imports = [ ../liam ];
vacu.underTest = true;
#systemd.tmpfiles.settings."69-whatever"."/run/secretKey".L.argument = "${testAgeSecretFile}";
systemd.services."acme-liam.dis8.net".enable = lib.mkForce false;
systemd.timers."acme-liam.dis8.net".enable = lib.mkForce false;
systemd.services."acme-selfsigned-liam.dis8.net".wantedBy = [ "postfix.service" "dovecot2.service" ];
systemd.services."acme-selfsigned-liam.dis8.net".before = [ "postfix.service" "dovecot2.service" ];
vacu.secretsFolder = "${sopsTestSecretsFolder}";
vacu.liam.relayhost = "[badhost.blarg]:587 [${relayDomain}]:587";
system.activationScripts.sopsHack.text = "ln -s ${testAgeSecretFile} /run/secretKey";
system.activationScripts.setupSecrets.deps = [ "sopsHack" ];
sops.age.keyFile = "/run/secretKey";
services.do-agent.enable = false;
virtualisation.digitalOcean = {
seedEntropy = false;
setSshKeys = false;
rebuildFromUserData = false;
setRootPassword = false;
nodes.liam =
{ lib, ... }:
{
imports = [
../common
../liam
];
vacu.underTest = true;
#systemd.tmpfiles.settings."69-whatever"."/run/secretKey".L.argument = "${testAgeSecretFile}";
systemd.services."acme-liam.dis8.net".enable = lib.mkForce false;
systemd.timers."acme-liam.dis8.net".enable = lib.mkForce false;
systemd.services."acme-selfsigned-liam.dis8.net".wantedBy = [
"postfix.service"
"dovecot2.service"
];
systemd.services."acme-selfsigned-liam.dis8.net".before = [
"postfix.service"
"dovecot2.service"
];
vacu.secretsFolder = "${sopsTestSecretsFolder}";
vacu.liam.relayhost = "[badhost.blarg]:587 [${relayDomain}]:587";
system.activationScripts.sopsHack.text = "ln -s ${testAgeSecretFile} /run/secretKey";
system.activationScripts.setupSecrets.deps = [ "sopsHack" ];
sops.age.keyFile = "/run/secretKey";
services.do-agent.enable = false;
virtualisation.digitalOcean = {
seedEntropy = false;
setSshKeys = false;
rebuildFromUserData = false;
setRootPassword = false;
};
# uncomment to significantly speed up the test
services.dovecot2.enableDHE = lib.mkForce false;
security.acme.defaults.email = lib.mkForce "me@example.org";
security.acme.defaults.server = lib.mkForce "https://example.com"; # self-signed only
networking.nameservers = lib.mkForce [ nodes.ns.networking.primaryIPAddress ];
security.pki.certificateFiles = [ rootCA.certificatePath ];
};
# uncomment to significantly speed up the test
services.dovecot2.enableDHE = lib.mkForce false;
security.acme.defaults.email = lib.mkForce "me@example.org";
security.acme.defaults.server = lib.mkForce "https://example.com"; # self-signed only
networking.nameservers = lib.mkForce [ nodes.ns.networking.primaryIPAddress ];
security.pki.certificateFiles = [ rootCA.certificatePath ];
};
nodes.checker = { pkgs, lib, ... }: {
environment.systemPackages = [
pkgs.wget
pkgs.python311Packages.imap-tools
pkgs.python311
(pkgs.writers.writePython3Bin "mailtest" { libraries = with pkgs.python3Packages; [ imap-tools requests ]; } ''
# flake8: noqa
# #!${pkgs.python311}/bin/python
import sys
sys.argv.insert(1, "${nodes.liam.networking.primaryIPAddress}")
#sys.path.append("${pkgs.python311Packages.imap-tools}/lib/python3.11/site-packages")
#sys.path.append("${pkgs.python311Packages.urllib3}/lib/python3.11/site-packages")
#sys.path.append("${pkgs.python311Packages.requests}/lib/python3.11/site-packages")
${builtins.readFile ./mailtest.py}
'')
];
networking.nameservers = lib.mkForce (lib.singleton nodes.ns.networking.primaryIPAddress);
};
nodes.checker =
{ pkgs, lib, ... }:
{
environment.systemPackages = [
pkgs.wget
pkgs.python311Packages.imap-tools
pkgs.python311
(pkgs.writers.writePython3Bin "mailtest"
{
libraries = with pkgs.python3Packages; [
imap-tools
requests
];
}
''
# flake8: noqa
# #!${pkgs.python311}/bin/python
import sys
sys.argv.insert(1, "${nodes.liam.networking.primaryIPAddress}")
#sys.path.append("${pkgs.python311Packages.imap-tools}/lib/python3.11/site-packages")
#sys.path.append("${pkgs.python311Packages.urllib3}/lib/python3.11/site-packages")
#sys.path.append("${pkgs.python311Packages.requests}/lib/python3.11/site-packages")
${builtins.readFile ./mailtest.py}
''
)
];
networking.nameservers = lib.mkForce (lib.singleton nodes.ns.networking.primaryIPAddress);
};
testScript = ''
start_all()
@@ -166,7 +216,9 @@ in {
liam.wait_for_unit("nginx.service")
liam.wait_for_open_port(80)
liam.copy_from_host("${pkgs.writeText "acme-test" "test"}", "${nodes.liam.security.acme.defaults.webroot + "/.well-known/acme-challenge/test"}")
liam.copy_from_host("${pkgs.writeText "acme-test" "test"}", "${
nodes.liam.security.acme.defaults.webroot + "/.well-known/acme-challenge/test"
}")
checker.succeed("wget http://liam.dis8.net/.well-known/acme-challenge/test")
liam.wait_for_unit("postfix.service")
@@ -193,15 +245,17 @@ in {
--rcptto superwow@shop.theviolincase.com --username julie
--rcptto roboman@vacu.store --username shelvacu
--mailfrom bob@vacu.store --expect-recipient-refused
--mailfrom shelvacu@shelvacu.com --expect-recipient-refused
--mailfrom julie@shelvacu.com --expect-recipient-refused
--mailfrom @vacu.store --expect-recipient-refused
--mailfrom bob@vacu.store --expect-refused
--mailfrom shelvacu@shelvacu.com --expect-refused
--mailfrom julie@shelvacu.com --expect-refused
--mailfrom @vacu.store --expect-refused
--mailfrom reject-spam-test@example.com --expect-refused
--submission --expect-recipient-refused --mailfrom julie@shelvacu.com --username shelvacu
--submission --expect-recipient-refused --mailfrom fubar@theviolincase.com --username shelvacu
--submission --expect-recipient-refused --mailfrom fubar@vacu.store --username julie
--submission --expect-refused --mailfrom julie@shelvacu.com --username shelvacu
--submission --expect-refused --mailfrom fubar@theviolincase.com --username shelvacu
--submission --expect-refused --mailfrom fubar@vacu.store --username julie
--submission --mailfrom shelvacu@shelvacu.com --rcptto foo@example.com --username shelvacu --password shelvacu --expect-sent
--submission --mailfrom shelvacu@shelvacu.com --rcptto foo@example.com --username shelvacu@shelvacu.com --password shelvacu --expect-sent

Some files were not shown because too many files have changed in this diff Show More