docs: secrets

This commit is contained in:
Ryan Yin
2024-01-31 11:41:34 +08:00
parent 3f9d23dbad
commit 6367c91f7a
+33 -13
View File
@@ -4,6 +4,9 @@
All my secrets are safely encrypted via agenix, and stored in a separate private GitHub repository and referenced as a flake input in this flake. All my secrets are safely encrypted via agenix, and stored in a separate private GitHub repository and referenced as a flake input in this flake.
The encryption is done by using all my host's public keys(`/etc/ssh/ssh_host_ed25519_key`), so that they can only be decrypted on any of my configured hosts.
The host keys are generated locally on each host by openssh without passphrase, and are only readable by `root`, and will never leave the host.
In this way, all secrets is still encrypted when transmitted over the network and written to `/nix/store`, In this way, all secrets is still encrypted when transmitted over the network and written to `/nix/store`,
they are decrypted only when they are finally used. they are decrypted only when they are finally used.
@@ -34,18 +37,24 @@ Suppose you want to add a new secret file `xxx.age`. Follow these steps:
# and users can decrypt the secrets by any of the corresponding private keys. # and users can decrypt the secrets by any of the corresponding private keys.
let let
# get user's ssh public key by command: # Get system's ssh public key by command:
# cat ~/.ssh/id_ed25519.pub
# if you do not have one, you can generate it by command:
# ssh-keygen -t ed25519
ryan = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIJx3Sk20pLL1b2PPKZey2oTyioODrErq83xG78YpFBoj";
users = [ ryan ];
# get system's ssh public key by command:
# cat /etc/ssh/ssh_host_ed25519_key.pub # cat /etc/ssh/ssh_host_ed25519_key.pub
ai = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAICGeXNCazqiqxn8TmbCRjA+pLWrxwenn+CFhizBMP6en root@ai"; # If you do not have this file, you can generate all the host keys by command:
systems = [ ai ]; # sudo ssh-keygen -A
in idol_ai = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAINHZtzeaQyXwuRMLzoOAuTu8P9bu5yc5MBwo5LI3iWBV root@ai";
harmonica = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAINT7Pgy/Yl+t6UkHp5+8zfeyJqeJ8EndyR1Vjf/XBe5f root@harmonica";
fern = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIMokXUYcUy7tysH4tRR6pevFjyOP4cXMjpBSgBZggm9X root@fern";
# A key for recovery purpose, generated by `ssh-keygen -t ed25519 -a 256 -C "ryan@agenix-recovery"` with a strong passphrase
# and keeped it offline in a safe place.
recovery_key = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIHnIGH+653Oe+GQaA8zjjj7HWMWp7bWXed4q5KqY4nqG ryan@agenix-recovery";
systems = [
idol_ai
harmonica
fern
recovery_key
];
{ {
"./xxx.age".publicKeys = users ++ systems; "./xxx.age".publicKeys = users ++ systems;
} }
@@ -117,7 +126,9 @@ Then, create `./secrets/default.nix` with the following content:
# if you changed this key, you need to regenerate all encrypt files from the decrypt contents! # if you changed this key, you need to regenerate all encrypt files from the decrypt contents!
age.identityPaths = [ age.identityPaths = [
"/home/ryan/.ssh/juliet-age" # using the host key for decryption
# the host key is generated on every host locally by openssh, and will never leave the host.
"/etc/ssh/ssh_host_ed25519_key"
]; ];
age.secrets."xxx" = { age.secrets."xxx" = {
@@ -141,9 +152,18 @@ NOTE: By default, `age.identityPaths` is set to `~/.ssh/id_ed25519` and `~/.ssh/
so make sure to place your decryption keys there. so make sure to place your decryption keys there.
If you're deploying to the same machine from which you encrypted the secrets, it should work out of the box. If you're deploying to the same machine from which you encrypted the secrets, it should work out of the box.
## Adding a new host
1. `cat` the public key of the new host, send it to an old host.
2. On the old host:
1. Add the public key to `secrets.nix`, and rekey all the secrets via `sudo agenix -r -i /etc/ssh/ssh_host_ed25519_key`.
2. Commit and push the changes to `nix-secrets`.
3. On the new host:
1. Clone this repo and run `nixos-rebuild switch` to deploy it, all the secrets will be decrypted automatically via the host private key.
## Other Replacements ## Other Replacements
- [ragenix](https://github.com/yaxitech/ragenix): A Rust reimplementation of agenix. - [ragenix](https://github.com/yaxitech/ragenix): A Rust reimplementation of agenix.
- agenix is mainly written in bash, and it's error message is quite obscure, a little typo may cause some errors no one can understand. - agenix is mainly written in bash, and it's error message is quite obscure, a little typo may cause some errors no one can understand.
- with a type-safe language like Rust, we can get a better error message and less bugs. - with a type-safe language like Rust, we can get a better error message and less bugs.