mirror of
https://github.com/cryptomator/cryptomator.git
synced 2026-08-19 13:46:04 +00:00
Implement changePassphrase from the secret-service API (#1191)
Fixes #1189
This commit is contained in:
@@ -28,4 +28,11 @@ public interface KeychainAccess {
|
||||
*/
|
||||
void deletePassphrase(String key) throws KeychainAccessException;
|
||||
|
||||
/**
|
||||
* Updates a passphrase with a given key.
|
||||
*
|
||||
* @param key Unique key previously used while {@link #storePassphrase(String, CharSequence) storing a passphrase}.
|
||||
* @param passphrase The secret to be updated in this keychain.
|
||||
*/
|
||||
void changePassphrase(String key, CharSequence passphrase) throws KeychainAccessException;
|
||||
}
|
||||
|
||||
+5
@@ -48,4 +48,9 @@ public class LinuxSecretServiceKeychainAccess implements KeychainAccessStrategy
|
||||
public void deletePassphrase(String key) throws KeychainAccessException {
|
||||
delegate.orElseThrow(IllegalStateException::new).deletePassphrase(key);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void changePassphrase(String key, CharSequence passphrase) throws KeychainAccessException {
|
||||
delegate.orElseThrow(IllegalStateException::new).changePassphrase(key, passphrase);
|
||||
}
|
||||
}
|
||||
|
||||
+15
-1
@@ -9,6 +9,8 @@ import java.util.Map;
|
||||
|
||||
class LinuxSecretServiceKeychainAccessImpl implements KeychainAccessStrategy {
|
||||
|
||||
private final String LABEL_FOR_SECRET_IN_KEYRING = "Cryptomator";
|
||||
|
||||
@Override
|
||||
public boolean isSupported() {
|
||||
try (@SuppressWarnings("unused") SimpleCollection keyring = new SimpleCollection()) {
|
||||
@@ -24,7 +26,7 @@ class LinuxSecretServiceKeychainAccessImpl implements KeychainAccessStrategy {
|
||||
try (SimpleCollection keyring = new SimpleCollection()) {
|
||||
List<String> list = keyring.getItems(createAttributes(key));
|
||||
if (list == null) {
|
||||
keyring.createItem("Cryptomator", passphrase, createAttributes(key));
|
||||
keyring.createItem(LABEL_FOR_SECRET_IN_KEYRING, passphrase, createAttributes(key));
|
||||
}
|
||||
} catch (IOException e) {
|
||||
throw new KeychainAccessException(e);
|
||||
@@ -57,6 +59,18 @@ class LinuxSecretServiceKeychainAccessImpl implements KeychainAccessStrategy {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void changePassphrase(String key, CharSequence passphrase) throws KeychainAccessException {
|
||||
try (SimpleCollection keyring = new SimpleCollection()) {
|
||||
List<String> list = keyring.getItems(createAttributes(key));
|
||||
if (list != null) {
|
||||
keyring.updateItem(list.get(0), LABEL_FOR_SECRET_IN_KEYRING, passphrase, createAttributes(key));
|
||||
}
|
||||
} catch (IOException e) {
|
||||
throw new KeychainAccessException(e);
|
||||
}
|
||||
}
|
||||
|
||||
private Map<String, String> createAttributes(String key) {
|
||||
Map<String, String> attributes = new HashMap();
|
||||
attributes.put("Vault", key);
|
||||
|
||||
@@ -46,4 +46,9 @@ class MacSystemKeychainAccess implements KeychainAccessStrategy {
|
||||
keychain().deletePassword(key);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void changePassphrase(String key, CharSequence passphrase) throws KeychainAccessException {
|
||||
storePassphrase(key, passphrase);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+5
@@ -112,6 +112,11 @@ class WindowsProtectedKeychainAccess implements KeychainAccessStrategy {
|
||||
saveKeychainEntries();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void changePassphrase(String key, CharSequence passphrase) throws KeychainAccessException {
|
||||
storePassphrase(key, passphrase);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSupported() {
|
||||
return SystemUtils.IS_OS_WINDOWS && winFunctions.isPresent() && !keychainPaths.isEmpty();
|
||||
|
||||
@@ -31,6 +31,12 @@ class MapKeychainAccess implements KeychainAccessStrategy {
|
||||
map.remove(key);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void changePassphrase(String key, CharSequence passphrase) {
|
||||
map.get(key);
|
||||
storePassphrase(key, passphrase);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSupported() {
|
||||
return true;
|
||||
|
||||
+20
-10
@@ -2,32 +2,28 @@ package org.cryptomator.ui.changepassword;
|
||||
|
||||
import javafx.beans.binding.Bindings;
|
||||
import javafx.beans.binding.BooleanBinding;
|
||||
import javafx.beans.property.IntegerProperty;
|
||||
import javafx.beans.property.ObjectProperty;
|
||||
import javafx.beans.property.SimpleIntegerProperty;
|
||||
import javafx.fxml.FXML;
|
||||
import javafx.scene.control.Button;
|
||||
import javafx.scene.control.CheckBox;
|
||||
import javafx.scene.control.Label;
|
||||
import javafx.scene.layout.HBox;
|
||||
import javafx.stage.Stage;
|
||||
import org.cryptomator.common.vaults.Vault;
|
||||
import org.cryptomator.cryptofs.CryptoFileSystemProvider;
|
||||
import org.cryptomator.cryptolib.api.InvalidPassphraseException;
|
||||
import org.cryptomator.keychain.KeychainAccess;
|
||||
import org.cryptomator.keychain.KeychainAccessException;
|
||||
import org.cryptomator.ui.common.Animations;
|
||||
import org.cryptomator.ui.common.ErrorComponent;
|
||||
import org.cryptomator.ui.common.FxController;
|
||||
import org.cryptomator.ui.controls.FontAwesome5IconView;
|
||||
import org.cryptomator.ui.controls.NiceSecurePasswordField;
|
||||
import org.cryptomator.ui.common.PasswordStrengthUtil;
|
||||
import org.fxmisc.easybind.EasyBind;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
import java.io.IOException;
|
||||
import java.util.ResourceBundle;
|
||||
import java.nio.CharBuffer;
|
||||
import java.util.Optional;
|
||||
|
||||
import static org.cryptomator.common.Constants.MASTERKEY_FILENAME;
|
||||
|
||||
@@ -40,17 +36,19 @@ public class ChangePasswordController implements FxController {
|
||||
private final Vault vault;
|
||||
private final ObjectProperty<CharSequence> newPassword;
|
||||
private final ErrorComponent.Builder errorComponent;
|
||||
private final Optional<KeychainAccess> keychain;
|
||||
|
||||
public NiceSecurePasswordField oldPasswordField;
|
||||
public CheckBox finalConfirmationCheckbox;
|
||||
public Button finishButton;
|
||||
|
||||
@Inject
|
||||
public ChangePasswordController(@ChangePasswordWindow Stage window, @ChangePasswordWindow Vault vault, @Named("newPassword") ObjectProperty<CharSequence> newPassword, ErrorComponent.Builder errorComponent) {
|
||||
public ChangePasswordController(@ChangePasswordWindow Stage window, @ChangePasswordWindow Vault vault, @Named("newPassword") ObjectProperty<CharSequence> newPassword, ErrorComponent.Builder errorComponent, Optional<KeychainAccess> keychain) {
|
||||
this.window = window;
|
||||
this.vault = vault;
|
||||
this.newPassword = newPassword;
|
||||
this.errorComponent = errorComponent;
|
||||
this.keychain = keychain;
|
||||
}
|
||||
|
||||
@FXML
|
||||
@@ -69,8 +67,9 @@ public class ChangePasswordController implements FxController {
|
||||
public void finish() {
|
||||
try {
|
||||
CryptoFileSystemProvider.changePassphrase(vault.getPath(), MASTERKEY_FILENAME, oldPasswordField.getCharacters(), newPassword.get());
|
||||
LOG.info("Successful changed password for {}", vault.getDisplayableName());
|
||||
LOG.info("Successfully changed password for {}", vault.getDisplayableName());
|
||||
window.close();
|
||||
updatePasswordInSystemkeychain();
|
||||
} catch (IOException e) {
|
||||
LOG.error("IO error occured during password change. Unable to perform operation.", e);
|
||||
errorComponent.cause(e).window(window).returnToScene(window.getScene()).build().showErrorScene();
|
||||
@@ -81,6 +80,17 @@ public class ChangePasswordController implements FxController {
|
||||
}
|
||||
}
|
||||
|
||||
private void updatePasswordInSystemkeychain() {
|
||||
if (keychain.isPresent()) {
|
||||
try {
|
||||
keychain.get().changePassphrase(vault.getId(), CharBuffer.wrap(newPassword.get()));
|
||||
LOG.info("Successfully updated password in system keychain for {}", vault.getDisplayableName());
|
||||
} catch (KeychainAccessException e) {
|
||||
LOG.error("Failed to update password in system keychain.", e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Getter/Setter */
|
||||
|
||||
public Vault getVault() {
|
||||
|
||||
Reference in New Issue
Block a user