support import and export of keystore labels in crypto-output qr codes

This commit is contained in:
Craig Raw 2023-08-30 14:22:18 +02:00
parent 0bc1dd96ed
commit 76dc294748
4 changed files with 17 additions and 7 deletions

2
drongo

@ -1 +1 @@
Subproject commit 8313d16e97e708e7674646d43d66cf08b052b863
Subproject commit bae4ce66051ebcb86c598105cd545b84b2578f1f

View file

@ -502,18 +502,22 @@ public class QRScanDialog extends Dialog<QRScanDialog.Result> {
if(cryptoOutput.getMultiKey() != null) {
MultiKey multiKey = cryptoOutput.getMultiKey();
Map<ExtendedKey, KeyDerivation> extendedPublicKeys = new LinkedHashMap<>();
Map<ExtendedKey, String> extendedPublicKeyLabels = new LinkedHashMap<>();
for(CryptoHDKey cryptoHDKey : multiKey.getHdKeys()) {
ExtendedKey extendedKey = getExtendedKey(cryptoHDKey);
KeyDerivation keyDerivation = getKeyDerivation(cryptoHDKey.getOrigin());
extendedPublicKeys.put(extendedKey, keyDerivation);
if(cryptoHDKey.getName() != null) {
extendedPublicKeyLabels.put(extendedKey, cryptoHDKey.getName());
}
return new OutputDescriptor(scriptType, multiKey.getThreshold(), extendedPublicKeys);
}
return new OutputDescriptor(scriptType, multiKey.getThreshold(), extendedPublicKeys, new LinkedHashMap<>(), extendedPublicKeyLabels);
} else if(cryptoOutput.getEcKey() != null) {
throw new IllegalArgumentException("EC keys are currently unsupported");
} else if(cryptoOutput.getHdKey() != null) {
ExtendedKey extendedKey = getExtendedKey(cryptoOutput.getHdKey());
KeyDerivation keyDerivation = getKeyDerivation(cryptoOutput.getHdKey().getOrigin());
return new OutputDescriptor(scriptType, extendedKey, keyDerivation);
return new OutputDescriptor(scriptType, extendedKey, keyDerivation, cryptoOutput.getHdKey().getName());
}
throw new IllegalStateException("CryptoOutput did not contain sufficient information");

View file

@ -271,7 +271,7 @@ public class KeystoreController extends WalletFormController implements Initiali
validationSupport.registerValidator(label, Validator.combine(
Validator.createEmptyValidator("Label is required"),
(Control c, String newValue) -> ValidationResult.fromErrorIf( c, "Label is not unique", walletForm.getWallet().getKeystores().stream().filter(k -> k != keystore).map(Keystore::getLabel).collect(Collectors.toList()).contains(newValue)),
(Control c, String newValue) -> ValidationResult.fromErrorIf( c, "Label is too long", newValue.replace(" ", "").length() > 16)
(Control c, String newValue) -> ValidationResult.fromErrorIf( c, "Label is too long", newValue.replace(" ", "").length() > Keystore.MAX_LABEL_LENGTH)
));
validationSupport.registerValidator(xpub, Validator.combine(
@ -551,6 +551,9 @@ public class KeystoreController extends WalletFormController implements Initiali
fingerprint.setText(keyDerivation.getMasterFingerprint());
derivation.setText(keyDerivation.getDerivationPath());
xpub.setText(extendedKey.toString());
if(result.outputDescriptor.getExtendedPublicKeyLabel(extendedKey) != null) {
label.setText(result.outputDescriptor.getExtendedPublicKeyLabel(extendedKey));
}
} else if(result.wallets != null) {
for(Wallet wallet : result.wallets) {
if(getWalletForm().getWallet().getScriptType().equals(wallet.getScriptType()) && !wallet.getKeystores().isEmpty()) {
@ -558,6 +561,9 @@ public class KeystoreController extends WalletFormController implements Initiali
fingerprint.setText(keystore.getKeyDerivation().getMasterFingerprint());
derivation.setText(keystore.getKeyDerivation().getDerivationPath());
xpub.setText(keystore.getExtendedPublicKey().toString());
if(!Keystore.DEFAULT_LABEL.equals(keystore.getLabel())) {
label.setText(keystore.getLabel());
}
return;
}
}

View file

@ -341,12 +341,12 @@ public class SettingsController extends WalletFormController implements Initiali
if(optionalResult.isPresent()) {
QRScanDialog.Result result = optionalResult.get();
if(result.outputDescriptor != null) {
setDescriptorText(result.outputDescriptor.toString());
replaceWallet(result.outputDescriptor.toWallet());
} else if(result.wallets != null) {
for(Wallet wallet : result.wallets) {
if(scriptType.getValue().equals(wallet.getScriptType()) && !wallet.getKeystores().isEmpty()) {
OutputDescriptor outputDescriptor = OutputDescriptor.getOutputDescriptor(wallet);
setDescriptorText(outputDescriptor.toString());
replaceWallet(outputDescriptor.toWallet());
break;
}
}
@ -425,7 +425,7 @@ public class SettingsController extends WalletFormController implements Initiali
CryptoCoinInfo cryptoCoinInfo = new CryptoCoinInfo(CryptoCoinInfo.Type.BITCOIN.ordinal(), Network.get() == Network.MAINNET ? CryptoCoinInfo.Network.MAINNET.ordinal() : CryptoCoinInfo.Network.TESTNET.ordinal());
List<PathComponent> pathComponents = keystore.getKeyDerivation().getDerivation().stream().map(cNum -> new IndexPathComponent(cNum.num(), cNum.isHardened())).collect(Collectors.toList());
CryptoKeypath cryptoKeypath = new CryptoKeypath(pathComponents, Utils.hexToBytes(keystore.getKeyDerivation().getMasterFingerprint()), pathComponents.size());
return new CryptoHDKey(false, extendedKey.getKey().getPubKey(), extendedKey.getKey().getChainCode(), cryptoCoinInfo, cryptoKeypath, null, extendedKey.getParentFingerprint());
return new CryptoHDKey(false, extendedKey.getKey().getPubKey(), extendedKey.getKey().getChainCode(), cryptoCoinInfo, cryptoKeypath, null, extendedKey.getParentFingerprint(), keystore.getLabel(), null);
}
public void editDescriptor(ActionEvent event) {