tangled
alpha
login
or
join now
karitham.dev
/
dotfiles
0
fork
atom
nix all the things
0
fork
atom
overview
issues
pulls
pipelines
pds on reg
karitham.dev
4 months ago
be581cf5
dd838f35
+245
-30
9 changed files
expand all
collapse all
unified
split
.sops.yaml
flake.lock
flake.nix
hosts
reg
default.nix
pds-backup.nix
pds.nix
secrets
cloudflare-api.env
pds-backup-s3.env
pds.env
+10
.sops.yaml
···
1
1
+
# https://github.com/Mic92/sops-nix
2
2
+
keys:
3
3
+
- &ozen age17cxj5zwkkxjkjvmpskpkyh6yt4xj4l8h6jyjxez3nmq6y9tvhqjsdp0m5j
4
4
+
- &server_reg age1j6j2ldpsj7jmchstwl3nktvatut9hzxnemmy6py84rrga5eaf93q5w8s39
5
5
+
creation_rules:
6
6
+
- path_regex: secrets/[^/]+\.(yaml|json|env|ini)$
7
7
+
key_groups:
8
8
+
- age:
9
9
+
- *ozen
10
10
+
- *server_reg
+24
-3
flake.lock
···
592
592
"niri": "niri",
593
593
"nixos-wsl": "nixos-wsl",
594
594
"nixpkgs": "nixpkgs_7",
595
595
+
"sops-nix": "sops-nix",
595
596
"ssh-keys": "ssh-keys",
596
597
"stable": "stable",
597
598
"starship-jj": "starship-jj",
···
678
679
"original": {
679
680
"owner": "oxalica",
680
681
"repo": "rust-overlay",
682
682
+
"type": "github"
683
683
+
}
684
684
+
},
685
685
+
"sops-nix": {
686
686
+
"inputs": {
687
687
+
"nixpkgs": [
688
688
+
"nixpkgs"
689
689
+
]
690
690
+
},
691
691
+
"locked": {
692
692
+
"lastModified": 1760998189,
693
693
+
"narHash": "sha256-ee2e1/AeGL5X8oy/HXsZQvZnae6XfEVdstGopKucYLY=",
694
694
+
"owner": "Mic92",
695
695
+
"repo": "sops-nix",
696
696
+
"rev": "5a7d18b5c55642df5c432aadb757140edfeb70b3",
697
697
+
"type": "github"
698
698
+
},
699
699
+
"original": {
700
700
+
"owner": "Mic92",
701
701
+
"repo": "sops-nix",
681
702
"type": "github"
682
703
}
683
704
},
···
809
830
"tree-sitter-nu": {
810
831
"flake": false,
811
832
"locked": {
812
812
-
"lastModified": 1761142283,
813
813
-
"narHash": "sha256-OSazwPrUD7kWz/oVeStnnXEJiDDmI7itiDPmg062Kl8=",
833
833
+
"lastModified": 1761314688,
834
834
+
"narHash": "sha256-WY1qZbRLLTKNcyt7eQTzoQ2YKwyWSuUpVdt3YST6yx8=",
814
835
"owner": "nushell",
815
836
"repo": "tree-sitter-nu",
816
816
-
"rev": "18b7f951e0c511f854685dfcc9f6a34981101dd6",
837
837
+
"rev": "47d4b4f5369c0cae866724758ae88ef07e10e4f1",
817
838
"type": "github"
818
839
},
819
840
"original": {
+5
-1
flake.nix
···
2
2
inputs = {
3
3
nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable";
4
4
stable.url = "github:NixOS/nixpkgs/nixos-25.05";
5
5
-
6
5
home-manager = {
7
6
url = "github:nix-community/home-manager";
8
7
inputs.nixpkgs.follows = "nixpkgs";
···
45
44
topiary-nushell = {
46
45
url = "github:blindFS/topiary-nushell";
47
46
flake = false;
47
47
+
};
48
48
+
49
49
+
sops-nix = {
50
50
+
url = "github:Mic92/sops-nix";
51
51
+
inputs.nixpkgs.follows = "nixpkgs";
48
52
};
49
53
};
50
54
outputs = inputs @ {
+9
-26
hosts/reg/default.nix
···
4
4
username,
5
5
...
6
6
}: {
7
7
-
imports = [./hardware.nix];
7
7
+
imports = [
8
8
+
inputs.sops-nix.nixosModules.sops
9
9
+
./hardware.nix
10
10
+
./pds.nix
11
11
+
./pds-backup.nix
12
12
+
];
8
13
9
14
boot.tmp.cleanOnBoot = true;
10
15
zramSwap.enable = true;
16
16
+
sops.age.sshKeyPaths = ["/etc/ssh/ssh_host_ed25519_key"];
11
17
services = {
12
18
tailscale.enable = true;
13
19
tailscale.useRoutingFeatures = "server";
···
17
23
enable = true;
18
24
host = "0.0.0.0";
19
25
};
20
20
-
21
21
-
writefreely = {
22
22
-
enable = true;
23
23
-
host = "notes.0xf.fr";
24
24
-
nginx.enable = true;
25
25
-
acme.enable = true;
26
26
-
settings = {
27
27
-
server.port = 3003;
28
28
-
app.host = "https://notes.0xf.fr";
29
29
-
app.site_name = "writefreely";
30
30
-
app.site_description = "writefreely";
31
31
-
app.single_user = true;
32
32
-
};
33
33
-
};
34
34
-
};
35
35
-
36
36
-
networking.firewall.allowedTCPPorts = [80 443];
37
37
-
38
38
-
security.acme = {
39
39
-
defaults.email = "netop@0xf.fr";
40
40
-
acceptTerms = true;
41
26
};
42
27
43
28
users.users = {
44
29
${username}.openssh.authorizedKeys.keyFiles = [inputs.ssh-keys];
45
30
};
46
31
47
47
-
environment.systemPackages = with pkgs; [helix writefreely];
32
32
+
environment.systemPackages = with pkgs; [helix];
48
33
server = true;
49
34
50
50
-
system = {
51
51
-
stateVersion = "25.05";
52
52
-
};
35
35
+
system.stateVersion = "25.05";
53
36
}
+109
hosts/reg/pds-backup.nix
···
1
1
+
{
2
2
+
config,
3
3
+
pkgs,
4
4
+
...
5
5
+
}: let
6
6
+
restoreScript = pkgs.writeShellScriptBin "pds-restore" ''
7
7
+
set -e
8
8
+
9
9
+
echo "Starting PDS restore..."
10
10
+
11
11
+
set -a
12
12
+
source ${config.sops.secrets.s3.path}
13
13
+
set +a
14
14
+
15
15
+
LATEST=$(${pkgs.awscli2}/bin/aws s3 ls s3://$S3_BUCKET/backups/ | sort | tail -1 | awk '{print $4}')
16
16
+
[ -z "$LATEST" ] && echo "No backups found." && exit 1
17
17
+
18
18
+
echo "Latest backup: $LATEST"
19
19
+
${pkgs.awscli2}/bin/aws s3 cp s3://$S3_BUCKET/backups/$LATEST /tmp/$LATEST
20
20
+
21
21
+
systemctl stop bluesky-pds
22
22
+
rm -rf /var/lib/pds/*
23
23
+
24
24
+
${pkgs.gnutar}/bin/tar -xzf /tmp/$LATEST -C /var/lib/pds
25
25
+
chown -R pds:pds /var/lib/pds
26
26
+
27
27
+
systemctl start bluesky-pds
28
28
+
29
29
+
echo "Restore completed."
30
30
+
'';
31
31
+
backupScript = pkgs.writeShellScript "pds-backup-script" ''
32
32
+
SOURCE_DIR="$PDS_DATA_DIR"
33
33
+
S3_BUCKET="$S3_BUCKET"
34
34
+
LOG_DIR="/var/log/pds-backup"
35
35
+
DATE_LABEL=$(date +"%Y%m%d-%H%M")
36
36
+
LOG_FILE="$LOG_DIR/$DATE_LABEL.log"
37
37
+
ARCHIVE_FILE="/tmp/pds-backup-$DATE_LABEL.tar.gz"
38
38
+
MAX_RETRIES=3
39
39
+
RETRY_INTERVAL=60
40
40
+
41
41
+
fail() {
42
42
+
echo "$(date): ERROR: $1" | tee -a "$LOG_FILE"
43
43
+
systemctl restart "$PDS_SERVICE" 2>/dev/null || echo "$(date): WARNING: Failed to restart PDS service after failure." >> "$LOG_FILE"
44
44
+
exit 1
45
45
+
}
46
46
+
47
47
+
mkdir -p "$LOG_DIR"
48
48
+
49
49
+
systemctl list-units --full -all | grep -Fq "$PDS_SERVICE.service" || fail "PDS service not found."
50
50
+
51
51
+
systemctl stop "$PDS_SERVICE" 2>/dev/null && echo "$(date): Stopped PDS service." >> "$LOG_FILE" || echo "$(date): Failed to stop PDS service." >> "$LOG_FILE"
52
52
+
53
53
+
[ -d "$SOURCE_DIR" ] || fail "Source directory $SOURCE_DIR does not exist."
54
54
+
"$TAR_CMD" -czf "$ARCHIVE_FILE" -C "$SOURCE_DIR" . 2>> "$LOG_FILE" || fail "Failed to create archive."
55
55
+
56
56
+
attempt=1
57
57
+
while [ $attempt -le $MAX_RETRIES ]; do
58
58
+
if "$AWS_CMD" s3 cp "$ARCHIVE_FILE" "s3://$S3_BUCKET/backups/$DATE_LABEL.tar.gz" 2>> "$LOG_FILE"; then
59
59
+
echo "$(date): Upload successful." >> "$LOG_FILE"
60
60
+
break
61
61
+
else
62
62
+
[ $attempt -lt $MAX_RETRIES ] && sleep $RETRY_INTERVAL || fail "Upload failed after retries."
63
63
+
fi
64
64
+
((attempt++))
65
65
+
done
66
66
+
67
67
+
rm -f "$ARCHIVE_FILE"
68
68
+
69
69
+
systemctl start "$PDS_SERVICE" 2>/dev/null || fail "Failed to start PDS service."
70
70
+
71
71
+
find "$LOG_DIR" -name "*.log" -mtime +90 -delete
72
72
+
[ $(find "$LOG_FILE" -mtime +30) ] && mv "$LOG_FILE" "$LOG_FILE.old" && touch "$LOG_FILE"
73
73
+
[ $(wc -l < "$LOG_FILE") -gt 1000 ] && mv "$LOG_FILE" "$LOG_FILE.old" && touch "$LOG_FILE"
74
74
+
75
75
+
echo "$(date): Backup completed." >> "$LOG_FILE"
76
76
+
'';
77
77
+
in {
78
78
+
sops.secrets.s3 = {
79
79
+
format = "dotenv";
80
80
+
sopsFile = ../../secrets/pds-backup-s3.env;
81
81
+
};
82
82
+
83
83
+
environment.systemPackages = [restoreScript];
84
84
+
85
85
+
systemd.services.pds-backup = {
86
86
+
description = "Backup PDS data to S3";
87
87
+
path = [pkgs.awscli2 pkgs.coreutils pkgs.gnutar pkgs.gzip];
88
88
+
serviceConfig = {
89
89
+
ExecStart = "${backupScript}";
90
90
+
Environment = [
91
91
+
"PDS_DATA_DIR=${config.services.bluesky-pds.settings.PDS_DATA_DIRECTORY}"
92
92
+
"PDS_SERVICE=bluesky-pds"
93
93
+
"TAR_CMD=${pkgs.gnutar}/bin/tar"
94
94
+
"AWS_CMD=${pkgs.awscli2}/bin/aws"
95
95
+
];
96
96
+
EnvironmentFile = [config.sops.secrets.s3.path];
97
97
+
User = "root";
98
98
+
Type = "oneshot";
99
99
+
};
100
100
+
};
101
101
+
102
102
+
systemd.timers.pds-backup = {
103
103
+
wantedBy = ["timers.target"];
104
104
+
timerConfig = {
105
105
+
OnCalendar = "daily";
106
106
+
Persistent = true;
107
107
+
};
108
108
+
};
109
109
+
}
+54
hosts/reg/pds.nix
···
1
1
+
{config, ...}: {
2
2
+
sops = {
3
3
+
secrets.pds = {
4
4
+
format = "dotenv";
5
5
+
sopsFile = ../../secrets/pds.env;
6
6
+
restartUnits = ["bluesky-pds.service"];
7
7
+
};
8
8
+
secrets.cloudflare-api = {
9
9
+
format = "dotenv";
10
10
+
sopsFile = ../../secrets/cloudflare-api.env;
11
11
+
};
12
12
+
};
13
13
+
14
14
+
services.bluesky-pds = {
15
15
+
enable = true;
16
16
+
settings = {
17
17
+
PDS_HOSTNAME = "0xf.fr";
18
18
+
};
19
19
+
environmentFiles = [config.sops.secrets.pds.path];
20
20
+
};
21
21
+
22
22
+
networking.firewall.allowedTCPPorts = [80 443];
23
23
+
24
24
+
security.acme = {
25
25
+
defaults.email = "netop@0xf.fr";
26
26
+
acceptTerms = true;
27
27
+
28
28
+
certs."0xf.fr" = {
29
29
+
dnsProvider = "cloudflare";
30
30
+
credentialsFile = config.sops.secrets.cloudflare-api.path;
31
31
+
group = config.services.nginx.group;
32
32
+
33
33
+
domain = "0xf.fr";
34
34
+
extraDomainNames = ["*.0xf.fr"];
35
35
+
reloadServices = ["nginx"];
36
36
+
};
37
37
+
};
38
38
+
39
39
+
services.nginx = let
40
40
+
pass = {
41
41
+
useACMEHost = "0xf.fr";
42
42
+
forceSSL = true;
43
43
+
locations."/" = {
44
44
+
proxyPass = "http://127.0.0.1:${builtins.toString config.services.bluesky-pds.settings.PDS_PORT}";
45
45
+
proxyWebsockets = true;
46
46
+
};
47
47
+
};
48
48
+
in {
49
49
+
enable = true;
50
50
+
recommendedProxySettings = true;
51
51
+
recommendedTlsSettings = true;
52
52
+
virtualHosts."~(.*)\\.0xf\\.fr$" = pass;
53
53
+
};
54
54
+
}
+9
secrets/cloudflare-api.env
···
1
1
+
CLOUDFLARE_DNS_API_TOKEN=ENC[AES256_GCM,data:+fg0tls3FnG8BsKs5Btl7CLJiTlKqhvI97y8NNttEODb3wcCnAikeQ==,iv:KvAw3rwYNnMrMBz45NYDs9Fmncn1zlllK40rphGA1Z0=,tag:UOPjy4YFKnmPx4Wao6O8kA==,type:str]
2
2
+
sops_age__list_0__map_enc=-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB4VkhkMExId0IrSllMcGdw\nZEJsWkpBYkN5ejRnVDNpUGlYK1NQN0cyRWxjClR0dDBOM1N3NytMeGljdFV0bGdB\nSkxDT3JHcllFMGJKdnUya0VXQVdqN1EKLS0tIE1XWDE0OUcvdDJwdjV5WTVUcXYr\nTkdLb09yNlMrUVBwTmNkUkJaSThVNTgKqJatfgKN9WVeN9zlUClFWq5hBfiAlfvC\nwOLPxrc/VzNeUYlP5kLpuhGtsLAhHii21r0dawZlekKFoMXaPleDLw==\n-----END AGE ENCRYPTED FILE-----\n
3
3
+
sops_age__list_0__map_recipient=age17cxj5zwkkxjkjvmpskpkyh6yt4xj4l8h6jyjxez3nmq6y9tvhqjsdp0m5j
4
4
+
sops_age__list_1__map_enc=-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB4OVhveExOajZRWFBicWpI\nMG80aEdvV3cyNGI4Q2lTZmxKOTBaT2ZvU0RRCnYwWFZ1T0QxY09ESEhmVDMxUHBB\nbmZwSWpNK0dGc1dGNlp1SWwwQVJDbGsKLS0tIEdseUJUZlhkbks2TWRVVkd6TFo5\ncGhnV2I5Q1NvYkFGbTkydVRHQm5ZTUkKBECA5NN+Gw8UBMvbdZ0Ky/LNDRCqcVYd\nQHEZgfhJh3PWcbfHGhZIl9ylYdcpv9LQ+3NZRr2VgRzL5TT1mpeGgA==\n-----END AGE ENCRYPTED FILE-----\n
5
5
+
sops_age__list_1__map_recipient=age1j6j2ldpsj7jmchstwl3nktvatut9hzxnemmy6py84rrga5eaf93q5w8s39
6
6
+
sops_lastmodified=2025-10-24T20:43:23Z
7
7
+
sops_mac=ENC[AES256_GCM,data:/+KeoI3T69vXm+duvhViX1a58LHmFxRXHLacpmpHZ+bDzp+8e26uPZ0hX00XqIQWv3xgez62r/LphaJmjvNoUhGe9lI12QjUpRtilAbDXLUpJVF2bYaQh08SdGcey4OhaTj7oITBMP+V2EVlhOx/T5/qfrWCZqkef4OKqSBBD7g=,iv:gWqyF7cQel9NtIEMYWGZ4vBDKWVwKbJpDTQVu9nb/Do=,tag:c+gT0jxGfhhSHRqr6YOv/g==,type:str]
8
8
+
sops_unencrypted_suffix=_unencrypted
9
9
+
sops_version=3.11.0
+12
secrets/pds-backup-s3.env
···
1
1
+
AWS_ACCESS_KEY_ID=ENC[AES256_GCM,data:5oKU0U+FeR666BTNL7gdb8Wnts/nvhCYDlGtetcq+Dc=,iv:i3i4ykyAR3tpfpDoke6renys9tZp/a6/JpRe7ajAnsg=,tag:S3yDGCIl+wG9tedXbcPbmw==,type:str]
2
2
+
AWS_SECRET_ACCESS_KEY=ENC[AES256_GCM,data:3UEACvF1q20QRdSxVcTrMJNsjZmSsGHmX0fq98KMvnJJffjYO6h+ClNT+38aDhgh8Dd2VRujYMVTI6RXPn28DQ==,iv:bBEs9lMhDMoeH3HymUQEOT8Y13457xcrevKI89nXBeg=,tag:eSekCTOKUu2u1S7/Mcy9sg==,type:str]
3
3
+
AWS_ENDPOINT_URL=ENC[AES256_GCM,data:bqp2c1pPg1ZWG2w8XF9dm+3wKMYFucxzNLmvlhoKYuIxJX5CZwUSrmDXsx4FXZtq0l2fIWUIMCRurE49Jq8QtL8M6GQ=,iv:j4uL5y6E3qd6KS7DALc/GdL2/HgpheQj2J/uuLZ7XZU=,tag:dWVbavob4IC02bY+EqfYGA==,type:str]
4
4
+
S3_BUCKET=ENC[AES256_GCM,data:1q3k8mjG6kM=,iv:3nktB4AvrGmH6MfIijV3mPajO9088UWfuBOeM99hwCQ=,tag:cfLCokyYHWqvtCeokIGrtg==,type:str]
5
5
+
sops_age__list_0__map_enc=-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSB2SkJUdWdYclR0U1pPUHpn\nc3pWSml5b3FOR3cvaVhNczJrbHA4NG83U1JZClVibTgyc3JBWC9LSXVJVmhZckxT\nSk1sN040MmRKd3BodUdFOVRxMTdGcUEKLS0tIHhjZUs5TXhhMm1nK3RQc3BJMTJG\nZmQ5cGlRbXNiczBwUnd1aTFaWk94bUkKjQEr03lQRuWxzQ6uTCRgpTj3C/FwBFwz\nQoYYAyqN5RBAJvN+7TFewgGgSBu+bE2RFazAxOizdXQXAmgceZnT5A==\n-----END AGE ENCRYPTED FILE-----\n
6
6
+
sops_age__list_0__map_recipient=age17cxj5zwkkxjkjvmpskpkyh6yt4xj4l8h6jyjxez3nmq6y9tvhqjsdp0m5j
7
7
+
sops_age__list_1__map_enc=-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBpdEo3Nlp6RmgvZER2ZWtS\nU2dFazU0Q2FndnZBL1g2Ky9lcjNKRDBoaGlBCmlIVG9iUXVmazkzb2NTeDhXKzhT\nc3JQZjhhb0h3VjI2b2tpcGxiVG9NQmMKLS0tIG9tTjlPLzVQSjRLSkw2djM5QzQ2\nenJ6RFJUazlmQStJRStudlhuV1Rsc1UKMaAFJszBkgONafeLGMYO1zzS+dHzX3Uh\n8wwni17QDZTTE5Q2P8KPBquVWyzh7UUI3GhbxuZhANfs/RA5AQlg2w==\n-----END AGE ENCRYPTED FILE-----\n
8
8
+
sops_age__list_1__map_recipient=age1j6j2ldpsj7jmchstwl3nktvatut9hzxnemmy6py84rrga5eaf93q5w8s39
9
9
+
sops_lastmodified=2025-10-24T22:20:59Z
10
10
+
sops_mac=ENC[AES256_GCM,data:h7telhUinjAmbijnepEv3NXjvtYuCvQzCfQ6PA5vqr9QY8kAUlqICLofOP9+SVocUR0LlXsoKfmLcdIMMpZG1Jb6D0PQ8RuG4sTm5BSrWvvPj+U/Cm8JuPAqtOie0vWPBsL8vHg9BQGrUWEVtiK9fBLVmEvafVj9mmKzbwBZNOg=,iv:hzi5UOVUAdQW2wY8fAxLysfaLUertVLYo1D4H9Ubz+4=,tag:fRB9Lerke0aDkmcu+OzIfw==,type:str]
11
11
+
sops_unencrypted_suffix=_unencrypted
12
12
+
sops_version=3.11.0
+13
secrets/pds.env
···
1
1
+
PDS_JWT_SECRET=ENC[AES256_GCM,data:7rkOzDdKVBgBIBDperVfo1lv39/TD5LrXeSto4+FT8s=,iv:eFUiIdDH5xxFxIxq4njilmTframihV99CYZQiKt9Wto=,tag:fHPsW6hudDKjhPnKHems0Q==,type:str]
2
2
+
PDS_ADMIN_PASSWORD=ENC[AES256_GCM,data:GHtiwkT7SMqTDP91CpsdBvakeg==,iv:ka8bXoFJL23P3TDkXON1yuF6z1NOfFjRRaGv5L2wAB4=,tag:FriN0YZAgAE/S5nwcMoGng==,type:str]
3
3
+
PDS_PLC_ROTATION_KEY_K256_PRIVATE_KEY_HEX=ENC[AES256_GCM,data:OjAyEohVNTmWKapzJX1e/ed6ZbWL3I5+SgM93Bm89qymJWGX90ssca+fAcny38g2sZJkiJWjfUulE5sTMAbGog==,iv:vquXtXGhDMEFNJ6tqE76HTv1PZtGjtIL3+K05eY7KxE=,tag:sVDuGtkxfYL6csJ4d80+dQ==,type:str]
4
4
+
PDS_EMAIL_SMTP_URL=ENC[AES256_GCM,data:u2ylh4YK4aR5WhOFTazwLk3i2CU71Yakcb3pyoc2D+i94KMX0xEWKLb0xKpBnKyVBEI9CLMpiLUOPR1CuJRVv/aOR4yBIA==,iv:/NuzdQxYq0r4z9iTLGRi4aa/qBxFp0NeyNIOxIoEjbY=,tag:3dhfx9BbMdTahW02mYwKjA==,type:str]
5
5
+
PDS_EMAIL_FROM_ADDRESS=ENC[AES256_GCM,data:Xqly+3nqg8VpOQ==,iv:Dx0YD81azbMt2iT6EaqmJRXCXxhycM/pyW9eFH1cHGE=,tag:zi6bE3BNu443IFaTZDe3Wg==,type:str]
6
6
+
sops_age__list_0__map_enc=-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBwS0dHSU9pd2tWVzZPZDlQ\nYVd6NjF0SkFrSGNUUUprUGN0c1Yzdk5BYXpZCnBiajU0cGVDQ0UwUVl6dHg5SjFO\nU3RScFhiTlZuYUJ6aC84K1F6YnEza2cKLS0tIDNFZ21BdHRTQTFGMkR3MDBxOHhG\nOVByYktJdjlsbTlNSDMvOTkvK0FyeU0KYBMndJPeIMpnqSrAUs0Em5Pbm7GBo/0e\nsaBKyYhn/pIPtJCyOiISqfXwMFHsiWCtd3dEejunG0x9eEkjWzDKqw==\n-----END AGE ENCRYPTED FILE-----\n
7
7
+
sops_age__list_0__map_recipient=age17cxj5zwkkxjkjvmpskpkyh6yt4xj4l8h6jyjxez3nmq6y9tvhqjsdp0m5j
8
8
+
sops_age__list_1__map_enc=-----BEGIN AGE ENCRYPTED FILE-----\nYWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSA2WW9pWHVZSWl4eWdCUGUv\nT3VSdVVPdVh0bENRanFjNnJVdlhQS2JvbzNRCmY2YnZmVlNhSDFYZ2VDWnN1MHp5\nS3lyMEpOa0hmTVdFeUtIQ1lrMWZVODgKLS0tIC93Q2hzb0pxdUNySEYwa1VyUjFN\nNk9tekkvUC9JT3NpcENqTHF5TUIyWXMKJ082QrvQ6QRfJ1RZqL9sSyKCmTLi+I9R\nxuo8E1SfP/204OQaihP6+9cCbLh3yYtESaAFw2Alisnoe4PvSR2I9g==\n-----END AGE ENCRYPTED FILE-----\n
9
9
+
sops_age__list_1__map_recipient=age1j6j2ldpsj7jmchstwl3nktvatut9hzxnemmy6py84rrga5eaf93q5w8s39
10
10
+
sops_lastmodified=2025-10-24T21:30:51Z
11
11
+
sops_mac=ENC[AES256_GCM,data:T7pttRlFl7HQwRY+AAXIX00wsABEyiHJsKPxXatl50Auaa+S3JJss56tVhphp2iMch7Z0nxnVT9kS03eAU1RUV0wHgCyu0QWNAib7PbUQIQvVq7pqF8SXORNuvwHJj2S9niASIDQqIenLYzUCRyq6tBnJ/XkW9JbiaOxs6w75G4=,iv:nvo7iAVjYkN45RZsqV3nGWzoaPcg74NRdhzy44lIi+Y=,tag:nIPrJy1srFn/nFTRjtdLbg==,type:str]
12
12
+
sops_unencrypted_suffix=_unencrypted
13
13
+
sops_version=3.11.0