From 080f7578fbf18e8dd5ae022853c53319e8646fda Mon Sep 17 00:00:00 2001 From: crschnick Date: Sat, 28 Feb 2026 07:38:46 +0000 Subject: [PATCH] Rework --- .../cred/PasswordManagerAgentStrategy.java | 5 ++- .../app/pwman/BitwardenPasswordManager.java | 14 ++++---- .../app/pwman/DashlanePasswordManager.java | 2 +- .../app/pwman/EnpassPasswordManager.java | 2 +- .../app/pwman/KeePassXcPasswordManager.java | 36 +++++-------------- .../app/pwman/KeeperPasswordManager.java | 10 +++--- .../app/pwman/LastpassPasswordManager.java | 2 +- .../xpipe/app/pwman/OnePasswordManager.java | 12 +++---- .../app/pwman/PassboltPasswordManager.java | 2 +- .../io/xpipe/app/pwman/PasswordManager.java | 2 +- .../app/pwman/PasswordManagerCommand.java | 2 +- .../xpipe/app/pwman/PsonoPasswordManager.java | 2 +- .../app/pwman/WindowsCredentialManager.java | 2 +- .../io/xpipe/app/util/AppJacksonModule.java | 6 ++++ .../PasswordManagerIdentityStore.java | 2 +- .../PasswordManagerIdentityStoreProvider.java | 7 ++-- lang/strings/translations_en.properties | 4 +-- 17 files changed, 48 insertions(+), 64 deletions(-) diff --git a/app/src/main/java/io/xpipe/app/cred/PasswordManagerAgentStrategy.java b/app/src/main/java/io/xpipe/app/cred/PasswordManagerAgentStrategy.java index f58642c96..17a2e6b05 100644 --- a/app/src/main/java/io/xpipe/app/cred/PasswordManagerAgentStrategy.java +++ b/app/src/main/java/io/xpipe/app/cred/PasswordManagerAgentStrategy.java @@ -4,7 +4,6 @@ import com.fasterxml.jackson.annotation.JsonTypeName; import io.xpipe.app.comp.base.ButtonComp; import io.xpipe.app.comp.base.HorizontalComp; import io.xpipe.app.comp.base.LabelComp; -import io.xpipe.app.comp.base.TextFieldComp; import io.xpipe.app.core.AppI18n; import io.xpipe.app.ext.ValidationException; import io.xpipe.app.platform.OptionsBuilder; @@ -46,7 +45,7 @@ public class PasswordManagerAgentStrategy implements SshIdentityStrategy { return AppI18n.get("passwordManagerEmpty"); } - if (!pwman.getKeyStrategy().supportsAgent()) { + if (!pwman.getKeyConfiguration().supportsAgent()) { return AppI18n.get("passwordManagerNoAgentSupport"); } @@ -87,7 +86,7 @@ public class PasswordManagerAgentStrategy implements SshIdentityStrategy { private PasswordManagerKeyConfiguration getConfig() { var pwman = AppPrefs.get().passwordManager().getValue(); - return pwman != null && pwman.getKeyStrategy() != null && pwman.getKeyStrategy().supportsAgent() ? pwman.getKeyStrategy() : null; + return pwman != null && pwman.getKeyConfiguration() != null && pwman.getKeyConfiguration().supportsAgent() ? pwman.getKeyConfiguration() : null; } @Override diff --git a/app/src/main/java/io/xpipe/app/pwman/BitwardenPasswordManager.java b/app/src/main/java/io/xpipe/app/pwman/BitwardenPasswordManager.java index a879e0927..6d3e644de 100644 --- a/app/src/main/java/io/xpipe/app/pwman/BitwardenPasswordManager.java +++ b/app/src/main/java/io/xpipe/app/pwman/BitwardenPasswordManager.java @@ -40,7 +40,7 @@ public class BitwardenPasswordManager implements PasswordManager { private static ShellControl SHELL; private static boolean copied; - private final PasswordManagerKeyStrategy agentStrategy; + private final PasswordManagerKeyStrategy keyStrategy; private static synchronized ShellControl getOrStartShell() throws Exception { if (SHELL == null) { @@ -61,7 +61,7 @@ public class BitwardenPasswordManager implements PasswordManager { @SuppressWarnings("unused") public static OptionsBuilder createOptions(Property p) { - var agentStrategy = new SimpleObjectProperty<>(p.getValue().agentStrategy); + var agentStrategy = new SimpleObjectProperty<>(p.getValue().keyStrategy); AtomicReference button = new AtomicReference<>(); var testButton = new ButtonComp(AppI18n.observable("sync"), new FontIcon("mdi2r-refresh"), () -> { @@ -84,10 +84,10 @@ public class BitwardenPasswordManager implements PasswordManager { return new OptionsBuilder() .addComp(testButton) - .nameAndDescription("passwordManagerAgentStrategy") + .nameAndDescription("passwordManagerKeyStrategy") .sub(agentStrategyChoice.build(), agentStrategy) .bind(() -> { - return BitwardenPasswordManager.builder().agentStrategy(agentStrategy.getValue()).build(); + return BitwardenPasswordManager.builder().keyStrategy(agentStrategy.getValue()).build(); }, p); } @@ -259,7 +259,7 @@ public class BitwardenPasswordManager implements PasswordManager { } @Override - public PasswordManagerKeyConfiguration getKeyStrategy() { + public PasswordManagerKeyConfiguration getKeyConfiguration() { return new PasswordManagerKeyConfiguration() { @Override public boolean supportsInlineSshKeys() { @@ -268,7 +268,7 @@ public class BitwardenPasswordManager implements PasswordManager { @Override public boolean supportsAgent() { - return agentStrategy != null; + return keyStrategy != null; } @Override @@ -278,7 +278,7 @@ public class BitwardenPasswordManager implements PasswordManager { @Override public SshIdentityStrategy getSshIdentityStrategy(String publicKey, boolean forward) { - return agentStrategy.getSshIdentityStrategy(publicKey, forward); + return keyStrategy.getSshIdentityStrategy(publicKey, forward); } }; } diff --git a/app/src/main/java/io/xpipe/app/pwman/DashlanePasswordManager.java b/app/src/main/java/io/xpipe/app/pwman/DashlanePasswordManager.java index a34682442..25192ea2f 100644 --- a/app/src/main/java/io/xpipe/app/pwman/DashlanePasswordManager.java +++ b/app/src/main/java/io/xpipe/app/pwman/DashlanePasswordManager.java @@ -80,7 +80,7 @@ public class DashlanePasswordManager implements PasswordManager { } @Override - public PasswordManagerKeyConfiguration getKeyStrategy() { + public PasswordManagerKeyConfiguration getKeyConfiguration() { return PasswordManagerKeyConfiguration.none(); } } diff --git a/app/src/main/java/io/xpipe/app/pwman/EnpassPasswordManager.java b/app/src/main/java/io/xpipe/app/pwman/EnpassPasswordManager.java index 3d338af96..de2f4bb7c 100644 --- a/app/src/main/java/io/xpipe/app/pwman/EnpassPasswordManager.java +++ b/app/src/main/java/io/xpipe/app/pwman/EnpassPasswordManager.java @@ -46,7 +46,7 @@ public class EnpassPasswordManager implements PasswordManager { private final FilePath vaultPath; @Override - public PasswordManagerKeyConfiguration getKeyStrategy() { + public PasswordManagerKeyConfiguration getKeyConfiguration() { return PasswordManagerKeyConfiguration.none(); } diff --git a/app/src/main/java/io/xpipe/app/pwman/KeePassXcPasswordManager.java b/app/src/main/java/io/xpipe/app/pwman/KeePassXcPasswordManager.java index 0b80da707..7f0c74a9b 100644 --- a/app/src/main/java/io/xpipe/app/pwman/KeePassXcPasswordManager.java +++ b/app/src/main/java/io/xpipe/app/pwman/KeePassXcPasswordManager.java @@ -41,40 +41,20 @@ public class KeePassXcPasswordManager implements PasswordManager { private static KeePassXcProxyClient client; private final List associationKeys; - private final PasswordManagerKeyStrategy agentStrategy; + private final PasswordManagerKeyStrategy keyStrategy; @Override - public PasswordManagerKeyConfiguration getKeyStrategy() { - return new PasswordManagerKeyConfiguration() { - @Override - public boolean supportsInlineSshKeys() { - return false; - } - - @Override - public boolean supportsAgent() { - return agentStrategy != null; - } - - @Override - public boolean supportsJoinedEntries() { - return false; - } - - @Override - public SshIdentityStrategy getSshIdentityStrategy(String publicKey, boolean forward) { - return agentStrategy.getSshIdentityStrategy(publicKey, forward); - } - }; + public PasswordManagerKeyConfiguration getKeyConfiguration() { + return PasswordManagerKeyConfiguration.of(false, false, keyStrategy); } @SuppressWarnings("unused") public static OptionsBuilder createOptions(Property p) { - var agentStrategy = new SimpleObjectProperty<>(p.getValue().getAgentStrategy()); + var keyStrategy = new SimpleObjectProperty<>(p.getValue().getKeyStrategy()); var agentStrategyChoice = OptionsChoiceBuilder.builder() .allowNull(true) .available(List.of(PasswordManagerKeyStrategy.KeePassXcOpenSshAgent.class, PasswordManagerKeyStrategy.KeePassXcPageant.class)) - .property(agentStrategy) + .property(keyStrategy) .build(); var prop = FXCollections.observableArrayList(); @@ -114,11 +94,11 @@ public class KeePassXcPasswordManager implements PasswordManager { })) .hide(Bindings.isEmpty(prop)) .addProperty(prop) - .nameAndDescription("passwordManagerAgentStrategy") - .sub(agentStrategyChoice.build(), agentStrategy) + .nameAndDescription("passwordManagerKeyStrategy") + .sub(agentStrategyChoice.build(), keyStrategy) .bind( () -> { - return new KeePassXcPasswordManager(prop, agentStrategy.getValue()); + return new KeePassXcPasswordManager(prop, keyStrategy.getValue()); }, p); } diff --git a/app/src/main/java/io/xpipe/app/pwman/KeeperPasswordManager.java b/app/src/main/java/io/xpipe/app/pwman/KeeperPasswordManager.java index efa7f0601..298b4b54e 100644 --- a/app/src/main/java/io/xpipe/app/pwman/KeeperPasswordManager.java +++ b/app/src/main/java/io/xpipe/app/pwman/KeeperPasswordManager.java @@ -40,11 +40,11 @@ import java.util.stream.Collectors; public class KeeperPasswordManager implements PasswordManager { @Override - public PasswordManagerKeyConfiguration getKeyStrategy() { - return PasswordManagerKeyConfiguration.of(true, true, agentStrategy); + public PasswordManagerKeyConfiguration getKeyConfiguration() { + return PasswordManagerKeyConfiguration.of(true, true, keyStrategy); } - private final PasswordManagerKeyStrategy agentStrategy; + private final PasswordManagerKeyStrategy keyStrategy; @JsonTypeInfo(use = JsonTypeInfo.Id.NAME, property = "type") public interface KeeperAuth { @@ -404,7 +404,7 @@ public class KeeperPasswordManager implements PasswordManager { @SuppressWarnings("unused") public static OptionsBuilder createOptions(Property p) { - var agentStrategy = new SimpleObjectProperty<>(p.getValue().getAgentStrategy()); + var agentStrategy = new SimpleObjectProperty<>(p.getValue().getKeyStrategy()); var mfa = new SimpleObjectProperty<>(p.getValue().getTwoFactorAuth() != null ? p.getValue().getTwoFactorAuth() : new KeeperAuth.None()); var choice = OptionsChoiceBuilder.builder() @@ -422,7 +422,7 @@ public class KeeperPasswordManager implements PasswordManager { return new OptionsBuilder() .nameAndDescription("keeper2fa") .sub(choice.build(), mfa) - .nameAndDescription("passwordManagerAgentStrategy") + .nameAndDescription("passwordManagerKeyStrategy") .sub(agentStrategyChoice.build(), agentStrategy) .bind( () -> { diff --git a/app/src/main/java/io/xpipe/app/pwman/LastpassPasswordManager.java b/app/src/main/java/io/xpipe/app/pwman/LastpassPasswordManager.java index 66eb979f3..bdacd1411 100644 --- a/app/src/main/java/io/xpipe/app/pwman/LastpassPasswordManager.java +++ b/app/src/main/java/io/xpipe/app/pwman/LastpassPasswordManager.java @@ -20,7 +20,7 @@ import java.util.Optional; public class LastpassPasswordManager implements PasswordManager { @Override - public PasswordManagerKeyConfiguration getKeyStrategy() { + public PasswordManagerKeyConfiguration getKeyConfiguration() { return PasswordManagerKeyConfiguration.none(); } diff --git a/app/src/main/java/io/xpipe/app/pwman/OnePasswordManager.java b/app/src/main/java/io/xpipe/app/pwman/OnePasswordManager.java index 9ee0b2438..48e3cfdaa 100644 --- a/app/src/main/java/io/xpipe/app/pwman/OnePasswordManager.java +++ b/app/src/main/java/io/xpipe/app/pwman/OnePasswordManager.java @@ -30,16 +30,16 @@ import java.util.regex.Pattern; public class OnePasswordManager implements PasswordManager { @Override - public PasswordManagerKeyConfiguration getKeyStrategy() { - return PasswordManagerKeyConfiguration.of(true, false, agentStrategy); + public PasswordManagerKeyConfiguration getKeyConfiguration() { + return PasswordManagerKeyConfiguration.of(true, false, keyStrategy); } private static ShellControl SHELL; - private final PasswordManagerKeyStrategy agentStrategy; + private final PasswordManagerKeyStrategy keyStrategy; @SuppressWarnings("unused") public static OptionsBuilder createOptions(Property p) { - var agentStrategy = new SimpleObjectProperty<>(p.getValue().getAgentStrategy()); + var agentStrategy = new SimpleObjectProperty<>(p.getValue().getKeyStrategy()); var agentStrategyChoice = OptionsChoiceBuilder.builder() .allowNull(true) @@ -48,10 +48,10 @@ public class OnePasswordManager implements PasswordManager { .build(); return new OptionsBuilder() - .nameAndDescription("passwordManagerAgentStrategy") + .nameAndDescription("passwordManagerKeyStrategy") .sub(agentStrategyChoice.build(), agentStrategy) .bind(() -> { - return OnePasswordManager.builder().agentStrategy(agentStrategy.getValue()).build(); + return OnePasswordManager.builder().keyStrategy(agentStrategy.getValue()).build(); }, p); } diff --git a/app/src/main/java/io/xpipe/app/pwman/PassboltPasswordManager.java b/app/src/main/java/io/xpipe/app/pwman/PassboltPasswordManager.java index 5a7f71426..0494ab22d 100644 --- a/app/src/main/java/io/xpipe/app/pwman/PassboltPasswordManager.java +++ b/app/src/main/java/io/xpipe/app/pwman/PassboltPasswordManager.java @@ -46,7 +46,7 @@ public class PassboltPasswordManager implements PasswordManager { private final Path privateKey; @Override - public PasswordManagerKeyConfiguration getKeyStrategy() { + public PasswordManagerKeyConfiguration getKeyConfiguration() { return PasswordManagerKeyConfiguration.none(); } diff --git a/app/src/main/java/io/xpipe/app/pwman/PasswordManager.java b/app/src/main/java/io/xpipe/app/pwman/PasswordManager.java index 78a72c747..88c81ce7d 100644 --- a/app/src/main/java/io/xpipe/app/pwman/PasswordManager.java +++ b/app/src/main/java/io/xpipe/app/pwman/PasswordManager.java @@ -44,7 +44,7 @@ public interface PasswordManager { String getWebsite(); - PasswordManagerKeyConfiguration getKeyStrategy(); + PasswordManagerKeyConfiguration getKeyConfiguration(); default Duration getCacheDuration() { return Duration.ofSeconds(30); diff --git a/app/src/main/java/io/xpipe/app/pwman/PasswordManagerCommand.java b/app/src/main/java/io/xpipe/app/pwman/PasswordManagerCommand.java index 460159d50..fb3d9fd11 100644 --- a/app/src/main/java/io/xpipe/app/pwman/PasswordManagerCommand.java +++ b/app/src/main/java/io/xpipe/app/pwman/PasswordManagerCommand.java @@ -33,7 +33,7 @@ public class PasswordManagerCommand implements PasswordManager { ShellScript script; @Override - public PasswordManagerKeyConfiguration getKeyStrategy() { + public PasswordManagerKeyConfiguration getKeyConfiguration() { return PasswordManagerKeyConfiguration.none(); } diff --git a/app/src/main/java/io/xpipe/app/pwman/PsonoPasswordManager.java b/app/src/main/java/io/xpipe/app/pwman/PsonoPasswordManager.java index aed16a54e..3dca7c559 100644 --- a/app/src/main/java/io/xpipe/app/pwman/PsonoPasswordManager.java +++ b/app/src/main/java/io/xpipe/app/pwman/PsonoPasswordManager.java @@ -38,7 +38,7 @@ public class PsonoPasswordManager implements PasswordManager { private final String serverUrl; @Override - public PasswordManagerKeyConfiguration getKeyStrategy() { + public PasswordManagerKeyConfiguration getKeyConfiguration() { return PasswordManagerKeyConfiguration.none(); } diff --git a/app/src/main/java/io/xpipe/app/pwman/WindowsCredentialManager.java b/app/src/main/java/io/xpipe/app/pwman/WindowsCredentialManager.java index a002fc5a6..40a820452 100644 --- a/app/src/main/java/io/xpipe/app/pwman/WindowsCredentialManager.java +++ b/app/src/main/java/io/xpipe/app/pwman/WindowsCredentialManager.java @@ -13,7 +13,7 @@ public class WindowsCredentialManager implements PasswordManager { private static boolean loaded = false; @Override - public PasswordManagerKeyConfiguration getKeyStrategy() { + public PasswordManagerKeyConfiguration getKeyConfiguration() { return PasswordManagerKeyConfiguration.none(); } diff --git a/app/src/main/java/io/xpipe/app/util/AppJacksonModule.java b/app/src/main/java/io/xpipe/app/util/AppJacksonModule.java index 26fd2797b..b8caa356f 100644 --- a/app/src/main/java/io/xpipe/app/util/AppJacksonModule.java +++ b/app/src/main/java/io/xpipe/app/util/AppJacksonModule.java @@ -107,6 +107,7 @@ public class AppJacksonModule extends SimpleModule { var object = JsonNodeFactory.instance.objectNode(); object.put("type", "keePassXc"); object.set("associationKeys", tree); + object.set("keyStrategy", JacksonMapper.getDefault().valueToTree(value.getKeyStrategy())); jgen.writeTree(object); } @@ -131,10 +132,14 @@ public class AppJacksonModule extends SimpleModule { return null; } + var keyStrategyNode = tree.get("keyStrategy"); + var keyStrategy = keyStrategyNode != null ? JacksonMapper.getDefault().treeToValue(keyStrategyNode, PasswordManagerKeyStrategy.class) : null; + if (tree.has("associationKey")) { var parsed = JacksonMapper.getDefault() .treeToValue(tree.required("associationKey"), KeePassXcAssociationKey.class); return KeePassXcPasswordManager.builder() + .keyStrategy(keyStrategy) .associationKeys(parsed != null ? List.of(parsed) : List.of()) .build(); } else { @@ -144,6 +149,7 @@ public class AppJacksonModule extends SimpleModule { var parsed = (List) JacksonMapper.getDefault().treeToValue(tree.required("associationKeys"), javaType); return KeePassXcPasswordManager.builder() + .keyStrategy(keyStrategy) .associationKeys(parsed) .build(); } diff --git a/ext/base/src/main/java/io/xpipe/ext/base/identity/PasswordManagerIdentityStore.java b/ext/base/src/main/java/io/xpipe/ext/base/identity/PasswordManagerIdentityStore.java index cd744f4de..6658aaa89 100644 --- a/ext/base/src/main/java/io/xpipe/ext/base/identity/PasswordManagerIdentityStore.java +++ b/ext/base/src/main/java/io/xpipe/ext/base/identity/PasswordManagerIdentityStore.java @@ -137,7 +137,7 @@ public class PasswordManagerIdentityStore extends IdentityStore return def; } - var strat = r.getKeyStrategy(); + var strat = r.getKeyConfiguration(); if (strat == null || (!strat.supportsInlineSshKeys() && !strat.supportsAgent())) { return def; } diff --git a/ext/base/src/main/java/io/xpipe/ext/base/identity/PasswordManagerIdentityStoreProvider.java b/ext/base/src/main/java/io/xpipe/ext/base/identity/PasswordManagerIdentityStoreProvider.java index fe252c27b..622f2a928 100644 --- a/ext/base/src/main/java/io/xpipe/ext/base/identity/PasswordManagerIdentityStoreProvider.java +++ b/ext/base/src/main/java/io/xpipe/ext/base/identity/PasswordManagerIdentityStoreProvider.java @@ -1,6 +1,6 @@ package io.xpipe.ext.base.identity; -import io.xpipe.app.cred.PasswordManagerAgentStrategy; +import io.xpipe.app.cred.SshIdentityStrategy; import io.xpipe.app.ext.DataStore; import io.xpipe.app.ext.DataStoreCreationCategory; import io.xpipe.app.ext.GuiDialog; @@ -8,7 +8,6 @@ import io.xpipe.app.platform.OptionsBuilder; import io.xpipe.app.platform.OptionsChoiceBuilder; import io.xpipe.app.prefs.AppPrefs; import io.xpipe.app.prefs.PasswordManagerTestComp; -import io.xpipe.app.pwman.PasswordManagerKeyConfiguration; import io.xpipe.app.storage.DataStorageUserHandler; import io.xpipe.app.storage.DataStoreCategory; import io.xpipe.app.storage.DataStoreEntry; @@ -37,10 +36,10 @@ public class PasswordManagerIdentityStoreProvider extends IdentityStoreProvider var perUser = new SimpleBooleanProperty(st.isPerUser()); var sshKeyChoice = OptionsChoiceBuilder.builder().allowNull(true) - .available(List.of(PasswordManagerAgentStrategy.class)).property(sshKey).build(); + .available(SshIdentityStrategy.getClasses()).property(sshKey).build(); var hideSshKeyChoice = Bindings.createBooleanBinding(() -> { var pwman = AppPrefs.get().passwordManager().getValue(); - var strat = pwman.getKeyStrategy(); + var strat = pwman.getKeyConfiguration(); return !strat.supportsAgent() || (strat.supportsJoinedEntries() && strat.supportsInlineSshKeys()); }); diff --git a/lang/strings/translations_en.properties b/lang/strings/translations_en.properties index 49ef33168..a4ac88b95 100644 --- a/lang/strings/translations_en.properties +++ b/lang/strings/translations_en.properties @@ -1997,8 +1997,8 @@ prefsRestartContent=Some options you changed require an application restart to a sshKey=SSH key inlineKey=Retrieve directly from CLI keyAgent=Use agent integration -passwordManagerAgentStrategy=SSH key retrieval method -passwordManagerAgentStrategyDescription=How and where to retrieve any stored SSH keys from. +passwordManagerKeyStrategy=SSH key retrieval method +passwordManagerKeyStrategyDescription=How and where to retrieve any stored SSH keys from. sshAgentNoKeys=The agent does not have any keys at the moment sshAgentHasKeys=The agent currently offers the following keys: passwordManagerNoAgentSupport=Password manager does not support retrieving SSH keys