Feature: Implement sops-nix:
- .sops.yaml: Rotate keys, narrow path_regex to secrets. - sops.nix: Init module, init `sops-nix` script. - configuration.nix: Add sops-nix to desktop configuration.
This commit is contained in:
parent
09c2066504
commit
efa8265c3b
24
.sops.yaml
24
.sops.yaml
@ -1,19 +1,9 @@
|
||||
keys:
|
||||
- &joey_desktop_jafner_net age1v5wy7epv5mm8ddf3cfv8m0e9w4s693dw7djpuytz9td8ycha5f0sv2se9n
|
||||
- &joey_age age1zswcq6t5wl8spr3g2wpxhxukjklngcav0vw8py0jnfkqd2jm2ypq53ga00
|
||||
creation_rules:
|
||||
- path_regex: .*
|
||||
# The below key_group and shamir_threshold configuration
|
||||
# allows any single author key to decrypt secrets,
|
||||
# but hosts and deploy runners *must* use both keys
|
||||
# to decrypt. This prevents a compromised host or
|
||||
# runner from leaking all secrets.
|
||||
shamir_threshold: 2
|
||||
- path_regex: ^.*(\.(secrets|token|passwd)|secrets.env|config.boot)
|
||||
key_groups:
|
||||
- age: # Author keys; to be held by contributors to the repo
|
||||
- 'age1zswcq6t5wl8spr3g2wpxhxukjklngcav0vw8py0jnfkqd2jm2ypq53ga00' # joey@dungeon-master
|
||||
- age: # Author keys (again); hacky way to give author keys a weight of 2 shares
|
||||
- 'age1zswcq6t5wl8spr3g2wpxhxukjklngcav0vw8py0jnfkqd2jm2ypq53ga00' # joey@dungeon-master
|
||||
- age: # Deploy keys; to be held by the deploy environment (e.g. Gitea Actions)
|
||||
- 'age193t908fjxl8ekl77p5xqnpj4xmw3y0khvyzlrw22hdzjduk6l53q05spq3' # deploy@gitea.jafner.tools
|
||||
- age: # Host key; to be held by hosts to which Stacks should be deployed
|
||||
- 'age13prhyye2jy3ysa6ltnjgkrqtxrxgs0035d86jyn4ltgk3wxtqgrqgav855' # fighter
|
||||
- 'age1n20krynrj75jqfy2muvhrygvzd4ee8ngamljqavsrk033zwx0ses2tdtfe' # druid
|
||||
- 'age1m0jpnk4t7hph5tdva3y9ap7scl8vfly9ufazr0h3cuwpcytlsulqjrt58y' # wizard
|
||||
- age:
|
||||
- *joey_desktop_jafner_net
|
||||
- *joey_age
|
||||
|
112
dotfiles/modules/sops.nix
Normal file
112
dotfiles/modules/sops.nix
Normal file
@ -0,0 +1,112 @@
|
||||
{ sys, pkgs, inputs, flake, ... }: {
|
||||
imports = [ inputs.sops-nix.nixosModules.sops ];
|
||||
sops = {
|
||||
age.sshKeyPaths = [ "${sys.ssh.path}/${sys.ssh.privateKey}" ];
|
||||
#age.keyFile = "/home/${sys.username}/.config/sops/age/keys.txt"; # This file is expected to be provided from outside the nix-store
|
||||
age.generateKey = false;
|
||||
};
|
||||
|
||||
home-manager.users.${sys.username}.home.packages = with pkgs; [
|
||||
sops
|
||||
age
|
||||
ssh-to-age
|
||||
( writeShellApplication {
|
||||
name = "sops-nix";
|
||||
runtimeInputs = [ git ssh-to-age openssh yq ];
|
||||
text = ''
|
||||
#! bash
|
||||
|
||||
# shellcheck disable=SC2002
|
||||
# shellcheck disable=SC2016
|
||||
|
||||
REPO_ROOT="/home/${sys.username}/${flake.repoPath}"
|
||||
# shellcheck disable=SC2034
|
||||
SOPS_AGE_KEY_FILE="/home/${sys.username}/.config/sops/age/keys.txt"
|
||||
|
||||
listSecrets () {
|
||||
# shellcheck disable=SC2002
|
||||
SOPS_REGEX="$(cat "$REPO_ROOT/.sops.yaml" | yq -y '.creation_rules.[].path_regex' | head -n1)"
|
||||
find "$REPO_ROOT" -regextype posix-extended -regex "$SOPS_REGEX"
|
||||
}
|
||||
|
||||
getPubkey () {
|
||||
ADDRESS="$1"
|
||||
AGE_PUBKEY="$(ssh-keyscan -t ed25519 "$ADDRESS" | ssh-to-age)"
|
||||
echo "$AGE_PUBKEY"
|
||||
}
|
||||
|
||||
addPubkey () { # Note: Does not edit any files. Prints .sops.yaml with the given key added.
|
||||
AGE_PUBKEY="$1"
|
||||
# shellcheck disable=SC2002,SC2016
|
||||
cat "$REPO_ROOT"/.sops.yaml |\
|
||||
yq -y --arg key "$AGE_PUBKEY" '.keys += [$key]' |\
|
||||
yq -y --arg key "$AGE_PUBKEY" '.creation_rules.[].key_groups.[].age += [$key]'
|
||||
}
|
||||
|
||||
updateKey () { # Note: Interactive
|
||||
sops updatekeys --input-type json "$1"
|
||||
}
|
||||
|
||||
encryptFile () { # Note: All encrypted files are in json format
|
||||
FILE="$1"
|
||||
FILE_EXT="''$''\{FILE##*.}"
|
||||
case "$FILE_EXT" in
|
||||
"env") FILE_TYPE=dotenv ;;
|
||||
"json") FILE_TYPE=json ;;
|
||||
"yaml|yml") FILE_TYPE=yaml ;;
|
||||
"ini") FILE_TYPE=ini ;;
|
||||
*) FILE_TYPE=binary ;;
|
||||
esac
|
||||
sops --encrypt --config "$REPO_ROOT/.sops.yaml" --input-type "$FILE_TYPE" --output-type json "$FILE"
|
||||
}
|
||||
|
||||
decryptFile () { # Note: All encrypted files are in json format.
|
||||
# File extension is used as the hint for decrypted file type.
|
||||
FILE="$1"
|
||||
FILE_EXT="''$''\{FILE##*.}"
|
||||
case "$FILE_EXT" in
|
||||
"env") FILE_TYPE=dotenv ;;
|
||||
"json") FILE_TYPE=json ;;
|
||||
"yaml|yml") FILE_TYPE=yaml ;;
|
||||
"ini") FILE_TYPE=ini ;;
|
||||
*) FILE_TYPE=binary ;;
|
||||
esac
|
||||
sops --decrypt --config "$REPO_ROOT/.sops.yaml" --input-type json --output-type "$FILE_TYPE" "$FILE"
|
||||
}
|
||||
|
||||
isJson () {
|
||||
FILE="$1"
|
||||
jq -e . >/dev/null 2>&1 <<<"$(cat "$FILE")" && return 0 || return 1;
|
||||
}
|
||||
|
||||
isEncrypted () {
|
||||
FILE="$1"
|
||||
FILE_EXT="''$''\{FILE##*.}"
|
||||
case "$FILE_EXT" in
|
||||
"env") FILE_TYPE=dotenv ;;
|
||||
"json") FILE_TYPE=json ;;
|
||||
"yaml|yml") FILE_TYPE=yaml ;;
|
||||
"ini") FILE_TYPE=ini ;;
|
||||
*) FILE_TYPE=binary ;;
|
||||
esac
|
||||
if isJson "$FILE" && [[ "$(sops filestatus "$FILE")" == '{"encrypted":true}' ]]; then echo True; else echo False; fi
|
||||
}
|
||||
|
||||
listSecretStatus () {
|
||||
for file in $(listSecrets); do
|
||||
FILE="$(realpath -s --relative-to="$REPO_ROOT" "$file")"
|
||||
echo -n "$FILE: " |\
|
||||
xargs echo -n
|
||||
if sops --decrypt --input-type json "$file" >/dev/null 2>&1; then
|
||||
echo Decryptable
|
||||
else
|
||||
echo "Not decryptable"
|
||||
fi
|
||||
done
|
||||
}
|
||||
|
||||
"$@"
|
||||
'';
|
||||
} )
|
||||
];
|
||||
}
|
@ -1,12 +1,17 @@
|
||||
{ sys, pkgs, inputs, ... }: {
|
||||
{ sys, pkgs, inputs, flake, ... }: {
|
||||
imports = [
|
||||
./hardware.nix
|
||||
./services.nix
|
||||
./desktop-environment.nix
|
||||
./terminal-environment.nix
|
||||
./theme.nix
|
||||
../../modules/sops.nix
|
||||
];
|
||||
|
||||
environment.sessionVariables = {
|
||||
"FLAKE_DIR" = "/home/${sys.username}/${flake.repoPath}/${flake.path}/";
|
||||
};
|
||||
|
||||
home-manager.backupFileExtension = "bk";
|
||||
home-manager.users."${sys.username}" = {
|
||||
nixGL = {
|
||||
|
Loading…
x
Reference in New Issue
Block a user