get rid of gpg

still looking into setting up another password manager

Signed-off-by: Gabriel Fontes <hi@m7.rs>
This commit is contained in:
Gabriel Fontes
2024-04-13 23:55:29 -03:00
parent 9e58d79c8f
commit f37e4b9528
19 changed files with 28 additions and 428 deletions
-1
View File
@@ -103,7 +103,6 @@ Most relevant user apps daily drivers:
- qutebrowser
- neomutt + mbsync
- khal + khard + todoman + vdirsyncer
- gpg + pass
- tailscale
- podman
- zathura
-1
View File
@@ -6,7 +6,6 @@
./fish.nix
./gh.nix
./git.nix
./gpg.nix
./jujutsu.nix
./lyrics.nix
./nix-index.nix
+6 -3
View File
@@ -51,9 +51,12 @@ in {
userEmail = "hi@m7.rs";
extraConfig = {
init.defaultBranch = "main";
user.signing.key = "CE707A2C17FAAC97907FF8EF2E54EA7BFE630916";
commit.gpgSign = true;
gpg.program = "${config.programs.gpg.package}/bin/gpg2";
gpg = {
format = "ssh";
ssh.defaultKeyCommand = "sh -c 'echo key::$(ssh-add -L | head -1)'";
};
commit.gpgsign = true;
merge.conflictStyle = "zdiff3";
commit.verbose = true;
@@ -1,7 +0,0 @@
{pkgs, ...}: let
ssh = "${pkgs.openssh}/bin/ssh";
gpg-connect-agent = "${pkgs.gnupg}/bin/gpg-connect-agent";
in {
isUnlocked = "${pkgs.procps}/bin/pgrep 'gpg-agent' &> /dev/null && ${gpg-connect-agent} 'scd getinfo card_list' /bye | ${pkgs.gnugrep}/bin/grep SERIALNO -q";
unlock = "${ssh} -T localhost -o StrictHostKeyChecking=no exit";
}
-68
View File
@@ -1,68 +0,0 @@
{
pkgs,
config,
lib,
...
}: {
services.gpg-agent = {
enable = true;
enableSshSupport = true;
sshKeys = ["149F16412997785363112F3DBD713BC91D51B831"];
enableExtraSocket = true;
pinentryPackage =
if config.gtk.enable
then pkgs.pinentry-gnome3
else pkgs.pinentry-tty;
};
home.packages = lib.optional config.gtk.enable pkgs.gcr;
programs = let
fixGpg =
/*
bash
*/
''
gpgconf --launch gpg-agent
'';
in {
# Start gpg-agent if it's not running or tunneled in
# SSH does not start it automatically, so this is needed to avoid having to use a gpg command at startup
# https://www.gnupg.org/faq/whats-new-in-2.1.html#autostart
bash.profileExtra = fixGpg;
fish.loginShellInit = fixGpg;
zsh.loginExtra = fixGpg;
gpg = {
enable = true;
settings = {
trust-model = "tofu+pgp";
};
publicKeys = [
{
source = ../../pgp.asc;
trust = 5;
}
];
};
};
systemd.user.services = {
# Link /run/user/$UID/gnupg to ~/.gnupg-sockets
# So that SSH config does not have to know the UID
link-gnupg-sockets = {
Unit = {
Description = "link gnupg sockets from /run to /home";
};
Service = {
Type = "oneshot";
ExecStart = "${pkgs.coreutils}/bin/ln -Tfs /run/user/%U/gnupg %h/.gnupg-sockets";
ExecStop = "${pkgs.coreutils}/bin/rm $HOME/.gnupg-sockets";
RemainAfterExit = true;
};
Install.WantedBy = ["default.target"];
};
};
}
# vim: filetype=nix
+13 -12
View File
@@ -1,6 +1,8 @@
{
outputs,
lib,
config,
pkgs,
...
}: let
hostnames = builtins.attrNames outputs.nixosConfigurations;
@@ -8,23 +10,22 @@ in {
programs.ssh = {
enable = true;
matchBlocks = {
net = {
host = builtins.concatStringsSep " " hostnames;
forwardAgent = true;
remoteForwards = [
{
bind.address = ''/%d/.gnupg-sockets/S.gpg-agent'';
host.address = ''/%d/.gnupg-sockets/S.gpg-agent.extra'';
}
];
};
trusted = lib.hm.dag.entryBefore ["net"] {
host = "m7.rs *.m7.rs *.ts.m7.rs";
trusted = {
host = "m7.rs *.m7.rs *.ts.m7.rs" + (builtins.concatStringsSep " " hostnames);
forwardAgent = true;
};
};
};
services.ssh-agent.enable = true;
home.sessionVariables = lib.mkIf config.gtk.enable {
SSH_ASKPASS_REQUIRE = "prefer";
SSH_ASKPASS = "${pkgs.gnome.seahorse}/libexec/seahorse/ssh-askpass";
};
systemd.user.services.ssh-agent.Service.Environment = [
"SSH_ASKPASS=${config.home.sessionVariables.SSH_ASKPASS or ""}"
];
home.persistence = {
"/persist/home/misterio".directories = [".ssh"];
};
@@ -91,7 +91,6 @@ in {
"pulseaudio"
"battery"
"custom/unread-mail"
"custom/gpg-agent"
];
modules-right = [
@@ -257,24 +256,6 @@ in {
"syncing" = "󰁪";
};
};
"custom/gpg-agent" = {
interval = 2;
return-type = "json";
exec = let
gpgCmds = import ../../../cli/gpg-commands.nix {inherit pkgs;};
in
jsonOutput "gpg-agent" {
pre = ''status=$(${gpgCmds.isUnlocked} && echo "unlocked" || echo "locked")'';
alt = "$status";
tooltip = "GPG is $status";
};
format = "{icon}";
format-icons = {
"locked" = "";
"unlocked" = "";
};
on-click = "";
};
"custom/gammastep" = {
interval = 5;
return-type = "json";
-7
View File
@@ -1,6 +1,5 @@
{
pkgs,
config,
...
}: {
programs.password-store = {
@@ -11,12 +10,6 @@
package = pkgs.pass.withExtensions (p: [p.pass-otp]);
};
services.pass-secret-service = {
enable = true;
storePath = "${config.home.homeDirectory}/.password-store";
extraArgs = ["-e${config.programs.password-store.package}/bin/pass"];
};
home.persistence = {
"/persist/home/misterio".directories = [".password-store"];
};
@@ -9,17 +9,12 @@
common = rec {
realName = "Gabriel Fontes";
gpg = {
key = "7088 C742 1873 E0DB 97FF 17C2 245C AB70 B4C2 25E9";
signByDefault = true;
};
signature = {
showSignature = "append";
text = ''
${realName}
https://gsfontes.com
PGP: ${gpg.key}
'';
};
};
@@ -113,31 +108,4 @@ in {
programs.mbsync.enable = true;
programs.msmtp.enable = true;
systemd.user.services.mbsync = {
Unit = {
Description = "mbsync synchronization";
};
Service = let
gpgCmds = import ../cli/gpg-commands.nix {inherit pkgs;};
in {
Type = "oneshot";
ExecCondition = ''
/bin/sh -c "${gpgCmds.isUnlocked}"
'';
ExecStart = "${mbsync} -a";
};
};
systemd.user.timers.mbsync = {
Unit = {
Description = "Automatic mbsync synchronization";
};
Timer = {
OnBootSec = "30";
OnUnitActiveSec = "5m";
};
Install = {
WantedBy = ["timers.target"];
};
};
}
@@ -1,11 +1,16 @@
{
pkgs,
lib,
config,
...
}: let
pass = "${config.programs.password-store.package}/bin/pass";
in {
services.vdirsyncer = {
enable = true;
};
programs.vdirsyncer = {
enable = true;
};
home.packages = with pkgs; [vdirsyncer];
home.persistence = {
@@ -59,31 +64,4 @@ in {
username = "hi@m7.rs"
password.fetch = ["command", "${pass}", "mail.m7.rs/hi@m7.rs"]
'';
systemd.user.services.vdirsyncer = {
Unit = {
Description = "vdirsyncer synchronization";
};
Service = let
gpgCmds = import ../cli/gpg-commands.nix {inherit pkgs;};
in {
Type = "oneshot";
ExecCondition = ''
/bin/sh -c "${gpgCmds.isUnlocked}"
'';
ExecStart = "${pkgs.vdirsyncer}/bin/vdirsyncer sync";
};
};
systemd.user.timers.vdirsyncer = {
Unit = {
Description = "Automatic vdirsyncer synchronization";
};
Timer = {
OnBootSec = "30";
OnUnitActiveSec = "5m";
};
Install = {
WantedBy = ["timers.target"];
};
};
}
+1
View File
@@ -1 +1,2 @@
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABgQDci4wJghnRRSqQuX1z2xeaUR+p/muKzac0jw0mgpXE2T/3iVlMJJ3UXJ+tIbySP6ezt0GVmzejNOvUarPAm0tOcW6W0Ejys2Tj+HBRU19rcnUtf4vsKk8r5PW5MnwS8DqZonP5eEbhW2OrX5ZsVyDT+Bqrf39p3kOyWYLXT2wA7y928g8FcXOZjwjTaWGWtA+BxAvbJgXhU9cl/y45kF69rfmc3uOQmeXpKNyOlTk6ipSrOfJkcHgNFFeLnxhJ7rYxpoXnxbObGhaNqn7gc5mt+ek+fwFzZ8j6QSKFsPr0NzwTFG80IbyiyrnC/MeRNh7SQFPAESIEP8LK3PoNx2l1M+MjCQXsb4oIG2oYYMRa2yx8qZ3npUOzMYOkJFY1uI/UEE/j/PlQSzMHfpmWus4o2sijfr8OmVPGeoU/UnVPyINqHhyAd1d3Iji3y3LMVemHtp5wVcuswABC7IRVVKZYrMCXMiycY5n00ch6XTaXBwCY00y8B3Mzkd7Ofq98YHc= hi@m7.rs
sk-ssh-ed25519@openssh.com AAAAGnNrLXNzaC1lZDI1NTE5QG9wZW5zc2guY29tAAAAICdJvqfMiqcqDfwonM1s6RI8wFfh9XR0jBMzlBDG/eZEAAAABHNzaDo= hi@m7.rs
@@ -39,10 +39,6 @@ in {
alias = ./scripts/nix-installer.sh;
};
"=/setup-gpg" = {
alias = ./scripts/setup-gpg.sh;
};
"=/7088C7421873E0DB97FF17C2245CAB70B4C225E9.asc".alias = pgpKey;
"=/pgp.asc".alias = pgpKey;
"=/pgp".alias = pgpKey;
@@ -1,44 +0,0 @@
#!/bin/sh
pgp_id="7088C7421873E0DB97FF17C2245CAB70B4C225E9"
ssh_keygrip="149F16412997785363112F3DBD713BC91D51B831"
set -eu
check_bin() {
if ! which "$1" > /dev/null; then
echo "'$1' is not available" >&2
exit 1
fi
}
check_bin gpg
check_bin pinentry
echo "GPG and Pinentry located" >&2
if ! gpg -k "$pgp_id" > /dev/null 2> /dev/null; then
echo "Downloading public key" >&2
gpg --receive-keys "$pgp_id"
fi
if ! gpg -K "$pgp_id" > /dev/null 2> /dev/null; then
echo "Searching card for private keystubs" >&2
gpg --card-status
fi
if ! grep -q "pinentry-program" ~/.gnupg/gpg-agent.conf 2>/dev/null; then
echo "pinentry-program $(readlink -f "$(which pinentry)")" >> ~/.gnupg/gpg-agent.conf
fi
if ! grep -q "enable-ssh-support" ~/.gnupg/gpg-agent.conf 2>/dev/null; then
echo "enable-ssh-support" >> ~/.gnupg/gpg-agent.conf
fi
if ! grep -q "$ssh_keygrip" ~/.gnupg/sshcontrol 2>/dev/null; then
echo "$ssh_keygrip" >> ~/.gnupg/sshcontrol
fi
echo "GPG configured" >&2
gpgconf --kill gpg-agent
gpgconf --launch gpg-agent
gpg-connect-agent updatestartuptty /bye
echo "GPG Agent restarted" >&2
+2 -1
View File
@@ -1,6 +1,7 @@
{
pkgs,
config,
lib,
...
}: let
ifTheyExist = groups: builtins.filter (group: builtins.hasAttr group config.users.groups) groups;
@@ -28,7 +29,7 @@ in {
"deluge"
];
openssh.authorizedKeys.keys = [(builtins.readFile ../../../../home/misterio/ssh.pub)];
openssh.authorizedKeys.keys = lib.splitString "\n" (builtins.readFile ../../../../home/misterio/ssh.pub);
hashedPasswordFile = config.sops.secrets.misterio-password.path;
packages = [pkgs.home-manager];
};
-1
View File
@@ -1,7 +1,6 @@
{
fonts = import ./fonts.nix;
monitors = import ./monitors.nix;
pass-secret-service = import ./pass-secret-service.nix;
rgbdaemon = import ./rgbdaemon.nix;
shellcolor = import ./shellcolor.nix;
wallpaper = import ./wallpaper.nix;
@@ -1,59 +0,0 @@
{
pkgs,
config,
lib,
...
}:
with lib; let
cfg = config.services.pass-secret-service;
in {
disabledModules = ["services/pass-secret-service.nix"];
meta.maintainers = with maintainers; [
cab404
cyntheticfox
];
options.services.pass-secret-service = {
enable = mkEnableOption "Pass libsecret service";
package = mkPackageOption pkgs "pass-secret-service" {};
storePath = mkOption {
type = with types; nullOr str;
default = null;
defaultText = "~/.password-store";
example = "/home/user/.local/share/password-store";
description = "Absolute path to password store.";
};
extraArgs = lib.mkOption {
type = with lib.types; listOf str;
default = [];
description = "Extra command-line arguments to be passed to the service.";
};
};
config = mkIf cfg.enable {
assertions = [(hm.assertions.assertPlatform "services.pass-secret-service" pkgs platforms.linux)];
services.pass-secret-service.extraArgs = optional (cfg.storePath != null) "--path=${cfg.storePath}";
systemd.user.services.pass-secret-service = {
Unit = {
AssertFileIsExecutable = "${cfg.package}/bin/pass_secret_service";
Description = "Pass libsecret service";
Documentation = "https://github.com/mdellweg/pass_secret_service";
PartOf = ["default.target"];
};
Service = {
ExecStart = "${cfg.package}/bin/pass_secret_service ${lib.escapeShellArgs cfg.extraArgs}";
};
Install = {
WantedBy = ["default.target"];
};
};
};
}
-3
View File
@@ -49,9 +49,6 @@ in {
pass-otp = addPatches prev.passExtensions.pass-otp [./pass-otp-fix-completion.patch];
};
# https://github.com/mdellweg/pass_secret_service/pull/37
pass-secret-service = addPatches prev.pass-secret-service [./pass-secret-service-native.diff];
# https://github.com/NixOS/nix/issues/7098
hydra_unstable = addPatches prev.hydra_unstable [./hydra-restrict-eval.diff];
-137
View File
@@ -1,137 +0,0 @@
diff --git a/Makefile b/Makefile
index 64222c2..65d4c33 100644
--- a/Makefile
+++ b/Makefile
@@ -3,6 +3,7 @@ relgnupghome ::= test/.gnupghome
export GNUPGHOME ::= $(projectdir)/$(relgnupghome)
gpg_key_id ::= "8c2a59a7"
relpassstore ::= test/.test-password-store
+pass ::= pypass
export PASSWORD_STORE_DIR ::= $(projectdir)/$(relpassstore)
.PHONY: all test coverage style clean clean-pycache clean-build
@@ -10,7 +11,7 @@ export PASSWORD_STORE_DIR ::= $(projectdir)/$(relpassstore)
all: style test
test: | $(relpassstore)
- dbus-run-session -- pytest-3 -v test
+ dbus-run-session -- pytest-3 -v test --asyncio-mode=auto
coverage: | $(relpassstore)
dbus-run-session -- python3 -m coverage run -m pytest -v test
@@ -28,7 +29,7 @@ $(relgnupghome): test/test_key.asc test/test_ownertrust.txt
$(relpassstore): | $(relgnupghome)
@echo "===== Preparing password store in $(relpassstore) ====="
- pypass init -p $(relpassstore) $(gpg_key_id)
+ $(pass) init -p $(relpassstore) $(gpg_key_id)
clean: clean-test-environment clean-pycache clean-build
diff --git a/pass_secret_service/common/native_pass.py b/pass_secret_service/common/native_pass.py
new file mode 100644
index 0000000..b1a06aa
--- /dev/null
+++ b/pass_secret_service/common/native_pass.py
@@ -0,0 +1,30 @@
+import subprocess
+import os
+
+DEFAULT_PASS = "pass"
+
+class NativePasswordStore:
+ def __init__(self, use_pass=None, path=None):
+ self.pass_cmd = use_pass or DEFAULT_PASS
+ self.path = path
+
+ def _pass(self, *args, **kwargs):
+ env = os.environ
+ if self.path is not None:
+ env.update({'PASSWORD_STORE_DIR': self.path})
+
+ proc = subprocess.run([self.pass_cmd, *args],
+ check=True,
+ text=True,
+ capture_output=True,
+ env=env,
+ **kwargs
+ )
+
+ return proc
+
+ def get_decrypted_password(self, passname):
+ return self._pass("show", passname).stdout.removesuffix("\n")
+
+ def insert_password(self, passname, password):
+ self._pass("insert", "--echo", passname, input=password)
diff --git a/pass_secret_service/common/pass_store.py b/pass_secret_service/common/pass_store.py
index c1aa175..4f13438 100644
--- a/pass_secret_service/common/pass_store.py
+++ b/pass_secret_service/common/pass_store.py
@@ -2,19 +2,30 @@
import shutil
import uuid
import json
-from pypass import PasswordStore
+try:
+ from pypass import PasswordStore
-# Work around a typo in pypass
-if not hasattr(PasswordStore, "get_decrypted_password"):
- PasswordStore.get_decrypted_password = PasswordStore.get_decypted_password
+ # Work around a typo in pypass
+ if not hasattr(PasswordStore, "get_decrypted_password"):
+ PasswordStore.get_decrypted_password = PasswordStore.get_decypted_password
+
+except ImportError:
+ from .native_pass import NativePasswordStore
+ PasswordStore = NativePasswordStore
class PassStore:
PREFIX = "secret_service"
- def __init__(self, *args, **kwargs):
- self._store = PasswordStore(*args, **kwargs)
+ def __init__(self, *args, use_pass=None, **kwargs):
+ if not use_pass:
+ self._store = PasswordStore(*args, **kwargs)
+
+ else:
+ from .native_pass import NativePasswordStore
+ self._store = NativePasswordStore(use_pass=use_pass, **kwargs)
+
self.base_path = os.path.join(self._store.path, self.PREFIX)
if not os.path.exists(self.base_path):
os.makedirs(self.base_path)
diff --git a/pass_secret_service/pass_secret_service.py b/pass_secret_service/pass_secret_service.py
index 8c35db9..7dbcdf0 100755
--- a/pass_secret_service/pass_secret_service.py
+++ b/pass_secret_service/pass_secret_service.py
@@ -30,10 +30,10 @@ async def register_service(pass_store):
return service
-def _main(path, verbose):
+def _main(path, pass_, verbose):
if verbose:
logging.basicConfig(level=20)
- pass_store = PassStore(**({"path": path} if path else {}))
+ pass_store = PassStore(use_pass=pass_, **({"path": path} if path else {}))
mainloop = asyncio.get_event_loop()
mainloop.add_signal_handler(signal.SIGTERM, functools.partial(term_loop, mainloop))
mainloop.add_signal_handler(signal.SIGINT, functools.partial(term_loop, mainloop))
@@ -51,9 +51,10 @@ def _main(path, verbose):
@click.command()
@click.option("--path", help="path to the password store (optional)")
+@click.option("-e", "pass_", help="use given pass executable")
@click.option("-v", "--verbose", help="be verbose", is_flag=True, default=False)
-def main(path, verbose):
- _main(path, verbose)
+def main(path, pass_, verbose):
+ _main(path, pass_, verbose)
if __name__ == "__main__": # pragma: no cover
-1
View File
@@ -21,7 +21,6 @@
sops
ssh-to-age
gnupg
age
];
};