use sops
for secret management
This commit is contained in:
parent
6eeea660f0
commit
cd820411c4
9 changed files with 95 additions and 25 deletions
9
.sops.yaml
Normal file
9
.sops.yaml
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
keys:
|
||||||
|
- &cswimr age1q9f9zhkfjn2c3a8qtmfqh0rtls3542jukqpt7t93jca6hc947f3sm9ujhx
|
||||||
|
- &eclipse age184ude6fyak8z4nnndq4nzcpe2d89zxf3r4paty7j2tenkwa6zgtqrz60lq
|
||||||
|
creation_rules:
|
||||||
|
- path_regex: secrets/[^/]+\.(yaml|json|env|ini)$
|
||||||
|
key_groups:
|
||||||
|
- age:
|
||||||
|
- *cswimr
|
||||||
|
- *eclipse
|
|
@ -1,7 +0,0 @@
|
||||||
keys:
|
|
||||||
- $eclipse age1q9f9zhkfjn2c3a8qtmfqh0rtls3542jukqpt7t93jca6hc947f3sm9ujhx
|
|
||||||
creation_rules:
|
|
||||||
- path_regex: secrets/[^/]+\.(yaml|json|env|ini|sops)$
|
|
||||||
key_groups:
|
|
||||||
- age:
|
|
||||||
- *eclipse
|
|
21
flake.lock
21
flake.lock
|
@ -532,9 +532,30 @@
|
||||||
"nixpkgs": "nixpkgs_3",
|
"nixpkgs": "nixpkgs_3",
|
||||||
"nixvim": "nixvim",
|
"nixvim": "nixvim",
|
||||||
"plasma-manager": "plasma-manager",
|
"plasma-manager": "plasma-manager",
|
||||||
|
"sops-nix": "sops-nix",
|
||||||
"zen-browser": "zen-browser"
|
"zen-browser": "zen-browser"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"sops-nix": {
|
||||||
|
"inputs": {
|
||||||
|
"nixpkgs": [
|
||||||
|
"nixpkgs"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"locked": {
|
||||||
|
"lastModified": 1733128155,
|
||||||
|
"narHash": "sha256-m6/qwJAJYcidGMEdLqjKzRIjapK4nUfMq7rDCTmZajc=",
|
||||||
|
"owner": "Mic92",
|
||||||
|
"repo": "sops-nix",
|
||||||
|
"rev": "c6134b6fff6bda95a1ac872a2a9d5f32e3c37856",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
"original": {
|
||||||
|
"owner": "Mic92",
|
||||||
|
"repo": "sops-nix",
|
||||||
|
"type": "github"
|
||||||
|
}
|
||||||
|
},
|
||||||
"systems": {
|
"systems": {
|
||||||
"locked": {
|
"locked": {
|
||||||
"lastModified": 1681028828,
|
"lastModified": 1681028828,
|
||||||
|
|
|
@ -11,6 +11,10 @@
|
||||||
inputs.nixpkgs.follows = "nixpkgs";
|
inputs.nixpkgs.follows = "nixpkgs";
|
||||||
inputs.home-manager.follows = "home-manager";
|
inputs.home-manager.follows = "home-manager";
|
||||||
};
|
};
|
||||||
|
sops-nix = {
|
||||||
|
url = "github:Mic92/sops-nix";
|
||||||
|
inputs.nixpkgs.follows = "nixpkgs";
|
||||||
|
};
|
||||||
nix-flatpak.url = "github:gmodena/nix-flatpak";
|
nix-flatpak.url = "github:gmodena/nix-flatpak";
|
||||||
nixvim = {
|
nixvim = {
|
||||||
url = "github:nix-community/nixvim";
|
url = "github:nix-community/nixvim";
|
||||||
|
@ -44,6 +48,7 @@
|
||||||
inherit pkgs;
|
inherit pkgs;
|
||||||
system = system;
|
system = system;
|
||||||
hostname = "eclipse";
|
hostname = "eclipse";
|
||||||
|
user = user;
|
||||||
};
|
};
|
||||||
modules = [
|
modules = [
|
||||||
# imports
|
# imports
|
||||||
|
@ -60,6 +65,7 @@
|
||||||
./nixos/nvim.nix
|
./nixos/nvim.nix
|
||||||
./nixos/pkg.nix
|
./nixos/pkg.nix
|
||||||
./nixos/shell.nix
|
./nixos/shell.nix
|
||||||
|
./nixos/sops.nix
|
||||||
./nixos/sudo.nix
|
./nixos/sudo.nix
|
||||||
./nixos/symlinks.nix
|
./nixos/symlinks.nix
|
||||||
./nixos/tailscale.nix
|
./nixos/tailscale.nix
|
||||||
|
@ -69,6 +75,7 @@
|
||||||
hardware.bluetooth.enable = true;
|
hardware.bluetooth.enable = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inputs.sops-nix.nixosModules.sops
|
||||||
inputs.nixvim.nixosModules.nixvim
|
inputs.nixvim.nixosModules.nixvim
|
||||||
inputs.nix-flatpak.nixosModules.nix-flatpak
|
inputs.nix-flatpak.nixosModules.nix-flatpak
|
||||||
|
|
||||||
|
|
13
nixos/sops.nix
Normal file
13
nixos/sops.nix
Normal file
|
@ -0,0 +1,13 @@
|
||||||
|
{ user, ... }:
|
||||||
|
{
|
||||||
|
sops = {
|
||||||
|
defaultSopsFile = ../secrets/secrets.yaml;
|
||||||
|
age.sshKeyPaths = [ "/etc/ssh/ssh_host_ed25519_key" ];
|
||||||
|
secrets = {
|
||||||
|
"zipline" = {
|
||||||
|
owner = user;
|
||||||
|
path = "/home/${user}/.secrets/zipline";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
|
@ -13,6 +13,8 @@ def notify(
|
||||||
icon: Path | None = None,
|
icon: Path | None = None,
|
||||||
desktop_entry: str | None = None,
|
desktop_entry: str | None = None,
|
||||||
) -> None:
|
) -> None:
|
||||||
|
if not which("notify-send"):
|
||||||
|
raise FileNotFoundError("notify-send is not installed.")
|
||||||
args = ["notify-send", "-a", application_name, "-u", urgency]
|
args = ["notify-send", "-a", application_name, "-u", urgency]
|
||||||
if category:
|
if category:
|
||||||
args.append("-c")
|
args.append("-c")
|
||||||
|
@ -21,6 +23,8 @@ def notify(
|
||||||
args.append("-i")
|
args.append("-i")
|
||||||
args.append(str(icon))
|
args.append(str(icon))
|
||||||
if desktop_entry:
|
if desktop_entry:
|
||||||
|
if not does_desktop_entry_exist(desktop_entry=desktop_entry):
|
||||||
|
raise FileNotFoundError("Desktop entry does not exist.")
|
||||||
args.append("-h")
|
args.append("-h")
|
||||||
args.append(f"string:desktop-entry:{desktop_entry}")
|
args.append(f"string:desktop-entry:{desktop_entry}")
|
||||||
args.append(title)
|
args.append(title)
|
||||||
|
@ -29,12 +33,15 @@ def notify(
|
||||||
subprocess.run(args)
|
subprocess.run(args)
|
||||||
|
|
||||||
|
|
||||||
def read_secret_file(secret: str) -> str:
|
def read_secret_file(secret: str, home: bool = False) -> str:
|
||||||
|
if home:
|
||||||
|
path = os.path.expanduser(f"~/.secrets/{secret}")
|
||||||
|
else:
|
||||||
path = f"/var/secrets/{secret}"
|
path = f"/var/secrets/{secret}"
|
||||||
if not os.path.exists(path):
|
if not os.path.exists(path):
|
||||||
raise FileNotFoundError(f"Secret file {path} does not exist or cannot be read.")
|
raise FileNotFoundError(f"Secret file {path} does not exist or cannot be read.")
|
||||||
with open(f"/var/secrets/{secret}", "r") as f:
|
with open(file=path, mode="r") as secret_file:
|
||||||
secret = f.read().strip()
|
secret = secret_file.read().strip()
|
||||||
if not secret:
|
if not secret:
|
||||||
raise ValueError(f"Secret file {path} is empty.")
|
raise ValueError(f"Secret file {path} is empty.")
|
||||||
return secret
|
return secret
|
||||||
|
|
|
@ -60,7 +60,7 @@ def spectacle_screenshot(
|
||||||
|
|
||||||
try:
|
try:
|
||||||
opts = [
|
opts = [
|
||||||
"zipline.py",
|
"/etc/nixos/scripts/py/zipline.py",
|
||||||
file_path,
|
file_path,
|
||||||
"--application-name",
|
"--application-name",
|
||||||
"Spectacle",
|
"Spectacle",
|
||||||
|
|
|
@ -5,12 +5,10 @@ import argparse
|
||||||
import mimetypes
|
import mimetypes
|
||||||
import os
|
import os
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from shutil import which
|
|
||||||
from typing import Any
|
from typing import Any
|
||||||
|
|
||||||
import requests # type: ignore
|
import requests # type: ignore
|
||||||
from common.common import ( # type: ignore
|
from common.common import ( # type: ignore
|
||||||
does_desktop_entry_exist,
|
|
||||||
notify,
|
notify,
|
||||||
read_secret_file,
|
read_secret_file,
|
||||||
)
|
)
|
||||||
|
@ -23,19 +21,11 @@ def zipline(
|
||||||
application_name: str | None = None,
|
application_name: str | None = None,
|
||||||
desktop_entry: str | None = None,
|
desktop_entry: str | None = None,
|
||||||
) -> Any:
|
) -> Any:
|
||||||
token = read_secret_file("zipline")
|
token = read_secret_file(secret="zipline", home=True)
|
||||||
|
|
||||||
if not os.path.isfile(file_path):
|
if not os.path.isfile(file_path):
|
||||||
raise FileNotFoundError(f"File at {file_path} does not exist.")
|
raise FileNotFoundError(f"File at {file_path} does not exist.")
|
||||||
|
|
||||||
use_notify_send = False
|
|
||||||
if application_name and desktop_entry:
|
|
||||||
if not does_desktop_entry_exist(desktop_entry=desktop_entry):
|
|
||||||
raise FileNotFoundError("Desktop entry does not exist.")
|
|
||||||
if not which("notify-send"):
|
|
||||||
raise FileNotFoundError("notify-send is not installed.")
|
|
||||||
use_notify_send = True
|
|
||||||
|
|
||||||
content_type = mimetypes.guess_type(file_path)[0] or "application/octet-stream"
|
content_type = mimetypes.guess_type(file_path)[0] or "application/octet-stream"
|
||||||
|
|
||||||
try:
|
try:
|
||||||
|
@ -55,7 +45,7 @@ def zipline(
|
||||||
copy(text=link)
|
copy(text=link)
|
||||||
print(f"Link copied to clipboard: {link}")
|
print(f"Link copied to clipboard: {link}")
|
||||||
|
|
||||||
if use_notify_send:
|
if application_name and desktop_entry:
|
||||||
notify(
|
notify(
|
||||||
application_name=application_name,
|
application_name=application_name,
|
||||||
title="Upload Successful",
|
title="Upload Successful",
|
||||||
|
@ -71,7 +61,7 @@ def zipline(
|
||||||
raise Exception(error_message)
|
raise Exception(error_message)
|
||||||
|
|
||||||
except BaseException as e:
|
except BaseException as e:
|
||||||
if use_notify_send:
|
if application_name and desktop_entry:
|
||||||
notify(
|
notify(
|
||||||
application_name=application_name,
|
application_name=application_name,
|
||||||
title="Upload Failed",
|
title="Upload Failed",
|
||||||
|
|
30
secrets/secrets.yaml
Normal file
30
secrets/secrets.yaml
Normal file
|
@ -0,0 +1,30 @@
|
||||||
|
zipline: ENC[AES256_GCM,data:YQMdw1cJy9wFnJsX6fPWBXK0rPEnuJJwJysVh0vggcnySFjl5Dmolaqxhw==,iv:RKB+rNz76ZxqzmyATLcpHmaap1f6aWWm7smBTieMZ8M=,tag:GN967VhwqZwMA6uzshKBmQ==,type:str]
|
||||||
|
sops:
|
||||||
|
kms: []
|
||||||
|
gcp_kms: []
|
||||||
|
azure_kv: []
|
||||||
|
hc_vault: []
|
||||||
|
age:
|
||||||
|
- recipient: age1q9f9zhkfjn2c3a8qtmfqh0rtls3542jukqpt7t93jca6hc947f3sm9ujhx
|
||||||
|
enc: |
|
||||||
|
-----BEGIN AGE ENCRYPTED FILE-----
|
||||||
|
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBabXF4b2dBelo1THZHOG9u
|
||||||
|
UWxNaEMwTlErTU1ZYmhISnVubXBBY3JaZkFjClFpblNFeWtwN0hrOGVTdThaQzFE
|
||||||
|
R0lqS2lYcDBWck9Pb3dmTk1yRS9rNFUKLS0tIFRUaUx2QlRmb0NFRlV3RndYbUpn
|
||||||
|
RHlURzRGL0grRFRDVGlVMTNpMlU5eUkKWzoCPqrcJBqM0H+Ap0v5Jsf69y7xV9gA
|
||||||
|
d9ubH84yMrOjLPs/K2FmLm+0zr7/epGE02nceiGzgWDHczQGp7qhzA==
|
||||||
|
-----END AGE ENCRYPTED FILE-----
|
||||||
|
- recipient: age184ude6fyak8z4nnndq4nzcpe2d89zxf3r4paty7j2tenkwa6zgtqrz60lq
|
||||||
|
enc: |
|
||||||
|
-----BEGIN AGE ENCRYPTED FILE-----
|
||||||
|
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSA1ZVdIRkMzMjErTjRpSC82
|
||||||
|
Rk04SmxVM3FiUys1VVViUmhQTkJKTW1MSjNNClg2KzA1M3lXTjVqVm52aXlxNDE1
|
||||||
|
cHl0VDB1MCtpdnVabStZRkoxQjlHQmcKLS0tIGs5WTZMUFNKcU5qQXVqUjFNTGVF
|
||||||
|
b1JvNi9YODZPN1FObWpOVHN3aU85NFEK1dN5pV8g3nG3D2l482z1JCRzmJ/9m495
|
||||||
|
YEobjXbEqQDhvA47ueWojoMjvQ3CgrPyiL6v+DLj7VfI5cyuo+89IQ==
|
||||||
|
-----END AGE ENCRYPTED FILE-----
|
||||||
|
lastmodified: "2024-12-03T01:29:28Z"
|
||||||
|
mac: ENC[AES256_GCM,data:NzE6V3kb9hiA9WAs7GFK5GqFoOUP5U/EOskWq0qdCo6GMewkK8TqrY+lFgjkEhY39PobgVTICBT8MGhY9eiEINYdBl7DuQGb3cR/puV+iCPEgUemzVcmcGkd24ktzUO2DsWet1EFC84oOu50XzYfR9VqW3z7+7UbpzWuOxIdvAA=,iv:pxNCxKPevqg8QxsIfL6+2pEB5cUmKhmLhmdiO+nB/Ac=,tag:uFA84z0XjzNgp3NLBu8AfQ==,type:str]
|
||||||
|
pgp: []
|
||||||
|
unencrypted_suffix: _unencrypted
|
||||||
|
version: 3.9.1
|
Loading…
Reference in a new issue