beignet 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.eslintignore +4 -0
- package/.eslintrc +40 -0
- package/.prettierrc +9 -0
- package/LICENSE +21 -0
- package/README.md +166 -0
- package/dist/electrum/constants.js +31 -0
- package/dist/electrum/constants.js.map +1 -0
- package/dist/electrum/index.js +552 -0
- package/dist/electrum/index.js.map +1 -0
- package/dist/index.js +23 -0
- package/dist/index.js.map +1 -0
- package/dist/shapes/electrum.js +14 -0
- package/dist/shapes/electrum.js.map +1 -0
- package/dist/shapes/index.js +19 -0
- package/dist/shapes/index.js.map +1 -0
- package/dist/shapes/wallet.js +115 -0
- package/dist/shapes/wallet.js.map +1 -0
- package/dist/transaction/index.js +692 -0
- package/dist/transaction/index.js.map +1 -0
- package/dist/types/electrum/constants.d.ts +7 -0
- package/dist/types/electrum/index.d.ts +85 -0
- package/dist/types/electrum.js +9 -0
- package/dist/types/electrum.js.map +1 -0
- package/dist/types/index.d.ts +6 -0
- package/dist/types/index.js +20 -0
- package/dist/types/index.js.map +1 -0
- package/dist/types/shapes/electrum.d.ts +5 -0
- package/dist/types/shapes/index.d.ts +2 -0
- package/dist/types/shapes/wallet.d.ts +10 -0
- package/dist/types/transaction/index.d.ts +92 -0
- package/dist/types/transaction.js +12 -0
- package/dist/types/transaction.js.map +1 -0
- package/dist/types/types/electrum.d.ts +113 -0
- package/dist/types/types/index.d.ts +3 -0
- package/dist/types/types/transaction.d.ts +51 -0
- package/dist/types/types/wallet.d.ts +400 -0
- package/dist/types/utils/conversion.d.ts +10 -0
- package/dist/types/utils/derivation-path.d.ts +19 -0
- package/dist/types/utils/electrum.d.ts +10 -0
- package/dist/types/utils/exchange-rate.d.ts +30 -0
- package/dist/types/utils/helpers.d.ts +23 -0
- package/dist/types/utils/index.d.ts +7 -0
- package/dist/types/utils/result.d.ts +16 -0
- package/dist/types/utils/transaction.d.ts +21 -0
- package/dist/types/utils/wallet.d.ts +47 -0
- package/dist/types/wallet/constants.d.ts +12 -0
- package/dist/types/wallet/index.d.ts +214 -0
- package/dist/types/wallet.js +36 -0
- package/dist/types/wallet.js.map +1 -0
- package/dist/utils/conversion.js +52 -0
- package/dist/utils/conversion.js.map +1 -0
- package/dist/utils/derivation-path.js +104 -0
- package/dist/utils/derivation-path.js.map +1 -0
- package/dist/utils/electrum.js +149 -0
- package/dist/utils/electrum.js.map +1 -0
- package/dist/utils/exchange-rate.js +49 -0
- package/dist/utils/exchange-rate.js.map +1 -0
- package/dist/utils/helpers.js +137 -0
- package/dist/utils/helpers.js.map +1 -0
- package/dist/utils/index.js +24 -0
- package/dist/utils/index.js.map +1 -0
- package/dist/utils/result.js +36 -0
- package/dist/utils/result.js.map +1 -0
- package/dist/utils/transaction.js +327 -0
- package/dist/utils/transaction.js.map +1 -0
- package/dist/utils/wallet.js +227 -0
- package/dist/utils/wallet.js.map +1 -0
- package/dist/wallet/constants.js +15 -0
- package/dist/wallet/constants.js.map +1 -0
- package/dist/wallet/index.js +2113 -0
- package/dist/wallet/index.js.map +1 -0
- package/docs/html/.nojekyll +1 -0
- package/docs/html/assets/highlight.css +22 -0
- package/docs/html/assets/main.js +58 -0
- package/docs/html/assets/search.js +1 -0
- package/docs/html/assets/style.css +1367 -0
- package/docs/html/classes/Electrum.html +812 -0
- package/docs/html/classes/Transaction.html +687 -0
- package/docs/html/classes/Wallet.html +2030 -0
- package/docs/html/enums/EAddressType.html +227 -0
- package/docs/html/enums/EAvailableNetworks.html +255 -0
- package/docs/html/enums/EBoostType.html +220 -0
- package/docs/html/enums/EFeeId.html +241 -0
- package/docs/html/enums/EPaymentType.html +220 -0
- package/docs/html/enums/EProtocol.html +220 -0
- package/docs/html/enums/EUnit.html +227 -0
- package/docs/html/functions/availableNetworks.html +200 -0
- package/docs/html/functions/constructByteCountParam.html +210 -0
- package/docs/html/functions/decodeOpReturnMessage.html +202 -0
- package/docs/html/functions/decodeRawTransaction.html +210 -0
- package/docs/html/functions/err.html +214 -0
- package/docs/html/functions/formatKeyDerivationPath.html +219 -0
- package/docs/html/functions/formatPeerData.html +207 -0
- package/docs/html/functions/generateMnemonic.html +223 -0
- package/docs/html/functions/generateWalletId.html +202 -0
- package/docs/html/functions/getAddressFromScriptPubKey.html +209 -0
- package/docs/html/functions/getAddressTypeFromPath.html +206 -0
- package/docs/html/functions/getByteCount.html +206 -0
- package/docs/html/functions/getDataFallback.html +207 -0
- package/docs/html/functions/getDefaultPort.html +209 -0
- package/docs/html/functions/getDefaultWalletData.html +200 -0
- package/docs/html/functions/getDefaultWalletDataKeys.html +200 -0
- package/docs/html/functions/getExchangeRates.html +200 -0
- package/docs/html/functions/getHighestUsedIndexFromTxHashes.html +216 -0
- package/docs/html/functions/getKeyDerivationPath.html +211 -0
- package/docs/html/functions/getKeyDerivationPathObject.html +216 -0
- package/docs/html/functions/getKeyDerivationPathString.html +220 -0
- package/docs/html/functions/getKeyValue.html +206 -0
- package/docs/html/functions/getPeers.html +211 -0
- package/docs/html/functions/getProtocolForPort.html +209 -0
- package/docs/html/functions/getScriptHash.html +210 -0
- package/docs/html/functions/getSeed.html +209 -0
- package/docs/html/functions/getSeedHash.html +206 -0
- package/docs/html/functions/getSha256.html +206 -0
- package/docs/html/functions/getStorageKeyValues.html +209 -0
- package/docs/html/functions/getTxFee.html +210 -0
- package/docs/html/functions/getWalletDataStorageKey.html +206 -0
- package/docs/html/functions/isValidBech32mEncodedString.html +211 -0
- package/docs/html/functions/objectKeys-1.html +211 -0
- package/docs/html/functions/objectsMatch.html +210 -0
- package/docs/html/functions/ok.html +214 -0
- package/docs/html/functions/parseOnChainPaymentRequest.html +204 -0
- package/docs/html/functions/reduceValue.html +215 -0
- package/docs/html/functions/removeDustOutputs.html +206 -0
- package/docs/html/functions/setReplaceByFee.html +210 -0
- package/docs/html/functions/shuffleArray.html +211 -0
- package/docs/html/functions/validateAddress.html +216 -0
- package/docs/html/functions/validateMnemonic.html +206 -0
- package/docs/html/functions/validateTransaction.html +206 -0
- package/docs/html/index.html +360 -0
- package/docs/html/interfaces/IAddInput.html +231 -0
- package/docs/html/interfaces/IAddress.html +247 -0
- package/docs/html/interfaces/IAddressData.html +231 -0
- package/docs/html/interfaces/IAddressType.html +199 -0
- package/docs/html/interfaces/IAddressTypeData.html +252 -0
- package/docs/html/interfaces/IAddresses.html +199 -0
- package/docs/html/interfaces/IBoostedTransaction.html +238 -0
- package/docs/html/interfaces/IBoostedTransactions.html +199 -0
- package/docs/html/interfaces/ICreateTransaction.html +224 -0
- package/docs/html/interfaces/ICustomGetAddress.html +231 -0
- package/docs/html/interfaces/ICustomGetScriptHash.html +224 -0
- package/docs/html/interfaces/IElectrumGetAddressBalanceRes.html +235 -0
- package/docs/html/interfaces/IExchangeRates.html +210 -0
- package/docs/html/interfaces/IFormattedPeerData.html +245 -0
- package/docs/html/interfaces/IFormattedTransaction.html +343 -0
- package/docs/html/interfaces/IFormattedTransactions.html +199 -0
- package/docs/html/interfaces/IGenerateAddresses.html +252 -0
- package/docs/html/interfaces/IGenerateAddressesResponse.html +224 -0
- package/docs/html/interfaces/IGetAddress.html +231 -0
- package/docs/html/interfaces/IGetAddressBalanceRes.html +226 -0
- package/docs/html/interfaces/IGetAddressByPath.html +224 -0
- package/docs/html/interfaces/IGetAddressHistoryResponse.html +269 -0
- package/docs/html/interfaces/IGetAddressResponse.html +231 -0
- package/docs/html/interfaces/IGetAddressScriptHashesHistoryResponse.html +245 -0
- package/docs/html/interfaces/IGetDerivationPath.html +259 -0
- package/docs/html/interfaces/IGetFeeEstimatesResponse.html +238 -0
- package/docs/html/interfaces/IGetHeaderResponse.html +245 -0
- package/docs/html/interfaces/IGetNextAvailableAddressResponse.html +238 -0
- package/docs/html/interfaces/IGetTransactions.html +245 -0
- package/docs/html/interfaces/IGetTransactionsFromInputs.html +245 -0
- package/docs/html/interfaces/IGetUtxosResponse.html +224 -0
- package/docs/html/interfaces/IHeader.html +231 -0
- package/docs/html/interfaces/IIndexes.html +238 -0
- package/docs/html/interfaces/IKeyDerivationPath.html +247 -0
- package/docs/html/interfaces/IKeyDerivationPathData.html +224 -0
- package/docs/html/interfaces/INewBlock.html +224 -0
- package/docs/html/interfaces/IOnchainFees.html +245 -0
- package/docs/html/interfaces/IOutput.html +231 -0
- package/docs/html/interfaces/IPeerData.html +231 -0
- package/docs/html/interfaces/IRbfData.html +252 -0
- package/docs/html/interfaces/ISend.html +224 -0
- package/docs/html/interfaces/ISendTransaction.html +322 -0
- package/docs/html/interfaces/ISendTx.html +231 -0
- package/docs/html/interfaces/ISetupTransaction.html +238 -0
- package/docs/html/interfaces/ISubscribeToAddress.html +247 -0
- package/docs/html/interfaces/ISubscribeToHeader.html +245 -0
- package/docs/html/interfaces/ITargets.html +238 -0
- package/docs/html/interfaces/ITransaction.html +281 -0
- package/docs/html/interfaces/ITxHash.html +217 -0
- package/docs/html/interfaces/ITxHashes.html +235 -0
- package/docs/html/interfaces/IUtxo.html +275 -0
- package/docs/html/interfaces/IVin.html +252 -0
- package/docs/html/interfaces/IVout.html +246 -0
- package/docs/html/interfaces/IWallet.html +350 -0
- package/docs/html/interfaces/IWalletData.html +343 -0
- package/docs/html/types/ElectrumConnectionPubSub.html +233 -0
- package/docs/html/types/ElectrumConnectionSubscription.html +204 -0
- package/docs/html/types/InputData.html +203 -0
- package/docs/html/types/ObjectKeys.html +198 -0
- package/docs/html/types/Result.html +201 -0
- package/docs/html/types/TAddressIndexInfo.html +204 -0
- package/docs/html/types/TAddressLabel.html +193 -0
- package/docs/html/types/TAddressType.html +193 -0
- package/docs/html/types/TAddressTypeContent.html +198 -0
- package/docs/html/types/TAddressTypes.html +193 -0
- package/docs/html/types/TAvailableNetworks.html +193 -0
- package/docs/html/types/TConnectToElectrumRes.html +193 -0
- package/docs/html/types/TDecodeRawTx.html +214 -0
- package/docs/html/types/TElectrumNetworks.html +193 -0
- package/docs/html/types/TGetAddressHistory.html +200 -0
- package/docs/html/types/TGetByteCountInput.html +193 -0
- package/docs/html/types/TGetByteCountInputs.html +193 -0
- package/docs/html/types/TGetByteCountOutput.html +193 -0
- package/docs/html/types/TGetByteCountOutputs.html +193 -0
- package/docs/html/types/TGetData.html +211 -0
- package/docs/html/types/TGetTotalFeeObj.html +204 -0
- package/docs/html/types/TKeyDerivationAccount.html +193 -0
- package/docs/html/types/TKeyDerivationChange.html +193 -0
- package/docs/html/types/TKeyDerivationCoinType.html +193 -0
- package/docs/html/types/TKeyDerivationIndex.html +193 -0
- package/docs/html/types/TKeyDerivationPurpose.html +193 -0
- package/docs/html/types/TMessageDataMap.html +210 -0
- package/docs/html/types/TMessageKeys.html +193 -0
- package/docs/html/types/TOnMessage.html +213 -0
- package/docs/html/types/TProcessUnconfirmedTransactions.html +202 -0
- package/docs/html/types/TProtocol.html +193 -0
- package/docs/html/types/TServer.html +204 -0
- package/docs/html/types/TSetData.html +213 -0
- package/docs/html/types/TSetupTransactionResponse.html +193 -0
- package/docs/html/types/TStorage.html +200 -0
- package/docs/html/types/TSubscribedReceive.html +193 -0
- package/docs/html/types/TTransactionMessage.html +198 -0
- package/docs/html/types/TTxResponse.html +206 -0
- package/docs/html/types/TTxResult.html +200 -0
- package/docs/html/types/TUnspentAddressScriptHashData.html +198 -0
- package/docs/html/types/TWalletDataKeys.html +193 -0
- package/docs/html/variables/defaultElectrumPorts.html +193 -0
- package/docs/html/variables/electrumConnection.html +199 -0
- package/docs/html/variables/mostUsedExchangeTickers.html +241 -0
- package/docs/markdown/.nojekyll +1 -0
- package/docs/markdown/README.md +1875 -0
- package/docs/markdown/classes/Electrum.md +718 -0
- package/docs/markdown/classes/Transaction.md +536 -0
- package/docs/markdown/classes/Wallet.md +2189 -0
- package/docs/markdown/enums/EAddressType.md +41 -0
- package/docs/markdown/enums/EAvailableNetworks.md +85 -0
- package/docs/markdown/enums/EBoostType.md +30 -0
- package/docs/markdown/enums/EFeeId.md +63 -0
- package/docs/markdown/enums/EPaymentType.md +30 -0
- package/docs/markdown/enums/EProtocol.md +30 -0
- package/docs/markdown/enums/EUnit.md +41 -0
- package/docs/markdown/interfaces/IAddInput.md +41 -0
- package/docs/markdown/interfaces/IAddress.md +69 -0
- package/docs/markdown/interfaces/IAddressData.md +41 -0
- package/docs/markdown/interfaces/IAddressType.md +7 -0
- package/docs/markdown/interfaces/IAddressTypeData.md +74 -0
- package/docs/markdown/interfaces/IAddresses.md +7 -0
- package/docs/markdown/interfaces/IBoostedTransaction.md +52 -0
- package/docs/markdown/interfaces/IBoostedTransactions.md +7 -0
- package/docs/markdown/interfaces/ICreateTransaction.md +30 -0
- package/docs/markdown/interfaces/ICustomGetAddress.md +41 -0
- package/docs/markdown/interfaces/ICustomGetScriptHash.md +30 -0
- package/docs/markdown/interfaces/IElectrumGetAddressBalanceRes.md +55 -0
- package/docs/markdown/interfaces/IExchangeRates.md +7 -0
- package/docs/markdown/interfaces/IFormattedPeerData.md +63 -0
- package/docs/markdown/interfaces/IFormattedTransaction.md +217 -0
- package/docs/markdown/interfaces/IFormattedTransactions.md +7 -0
- package/docs/markdown/interfaces/IGenerateAddresses.md +74 -0
- package/docs/markdown/interfaces/IGenerateAddressesResponse.md +30 -0
- package/docs/markdown/interfaces/IGetAddress.md +41 -0
- package/docs/markdown/interfaces/IGetAddressBalanceRes.md +36 -0
- package/docs/markdown/interfaces/IGetAddressByPath.md +30 -0
- package/docs/markdown/interfaces/IGetAddressHistoryResponse.md +121 -0
- package/docs/markdown/interfaces/IGetAddressResponse.md +41 -0
- package/docs/markdown/interfaces/IGetAddressScriptHashesHistoryResponse.md +63 -0
- package/docs/markdown/interfaces/IGetDerivationPath.md +100 -0
- package/docs/markdown/interfaces/IGetFeeEstimatesResponse.md +52 -0
- package/docs/markdown/interfaces/IGetHeaderResponse.md +63 -0
- package/docs/markdown/interfaces/IGetNextAvailableAddressResponse.md +52 -0
- package/docs/markdown/interfaces/IGetTransactions.md +63 -0
- package/docs/markdown/interfaces/IGetTransactionsFromInputs.md +63 -0
- package/docs/markdown/interfaces/IGetUtxosResponse.md +30 -0
- package/docs/markdown/interfaces/IHeader.md +41 -0
- package/docs/markdown/interfaces/IIndexes.md +52 -0
- package/docs/markdown/interfaces/IKeyDerivationPath.md +69 -0
- package/docs/markdown/interfaces/IKeyDerivationPathData.md +30 -0
- package/docs/markdown/interfaces/INewBlock.md +30 -0
- package/docs/markdown/interfaces/IOnchainFees.md +63 -0
- package/docs/markdown/interfaces/IOutput.md +41 -0
- package/docs/markdown/interfaces/IPeerData.md +41 -0
- package/docs/markdown/interfaces/IRbfData.md +74 -0
- package/docs/markdown/interfaces/ISend.md +30 -0
- package/docs/markdown/interfaces/ISendTransaction.md +184 -0
- package/docs/markdown/interfaces/ISendTx.md +41 -0
- package/docs/markdown/interfaces/ISetupTransaction.md +52 -0
- package/docs/markdown/interfaces/ISubscribeToAddress.md +60 -0
- package/docs/markdown/interfaces/ISubscribeToHeader.md +59 -0
- package/docs/markdown/interfaces/ITargets.md +52 -0
- package/docs/markdown/interfaces/ITransaction.md +88 -0
- package/docs/markdown/interfaces/ITxHash.md +19 -0
- package/docs/markdown/interfaces/ITxHashes.md +55 -0
- package/docs/markdown/interfaces/IUtxo.md +112 -0
- package/docs/markdown/interfaces/IVin.md +70 -0
- package/docs/markdown/interfaces/IVout.md +52 -0
- package/docs/markdown/interfaces/IWallet.md +209 -0
- package/docs/markdown/interfaces/IWalletData.md +217 -0
- package/example/helpers.ts +76 -0
- package/example/index.ts +77 -0
- package/package.json +69 -0
- package/src/electrum/constants.ts +28 -0
- package/src/electrum/index.ts +838 -0
- package/src/index.ts +6 -0
- package/src/shapes/electrum.ts +13 -0
- package/src/shapes/index.ts +2 -0
- package/src/shapes/wallet.ts +133 -0
- package/src/transaction/index.ts +1078 -0
- package/src/types/electrum.ts +139 -0
- package/src/types/index.ts +3 -0
- package/src/types/transaction.ts +58 -0
- package/src/types/wallet.ts +503 -0
- package/src/utils/conversion.ts +88 -0
- package/src/utils/derivation-path.ts +171 -0
- package/src/utils/electrum.ts +188 -0
- package/src/utils/exchange-rate.ts +70 -0
- package/src/utils/helpers.ts +191 -0
- package/src/utils/index.ts +7 -0
- package/src/utils/result.ts +79 -0
- package/src/utils/transaction.ts +417 -0
- package/src/utils/wallet.ts +351 -0
- package/src/wallet/constants.ts +24 -0
- package/src/wallet/index.ts +3304 -0
- package/tests/constants.ts +9 -0
- package/tests/derivation.test.ts +146 -0
- package/tests/electrum.test.ts +137 -0
- package/tests/storage.test.ts +222 -0
- package/tests/transaction.test.ts +187 -0
- package/tests/wallet.test.ts +307 -0
- package/tsconfig.json +32 -0
- package/typedoc.json +5 -0
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
import { default as bitcoinUnits } from 'bitcoin-units';
|
|
2
|
+
import { EUnit } from '../types';
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Converts a value in BTC to satoshis
|
|
6
|
+
* @param {number} value
|
|
7
|
+
* @returns {number}
|
|
8
|
+
*/
|
|
9
|
+
export const btcToSats = (value: number): number => {
|
|
10
|
+
try {
|
|
11
|
+
return Number(bitcoinUnits(value, 'BTC').to('satoshi').value().toFixed(0));
|
|
12
|
+
} catch {
|
|
13
|
+
return 0;
|
|
14
|
+
}
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
/**
|
|
18
|
+
* Converts a value in satoshis to BTC
|
|
19
|
+
* @param {number} value
|
|
20
|
+
* @returns {number}
|
|
21
|
+
*/
|
|
22
|
+
export const satsToBtc = (value: number): number => {
|
|
23
|
+
return bitcoinUnits(value, 'sats').to('BTC').value();
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
/**
|
|
27
|
+
* Converts an amount of currency in a specific unit to satoshis
|
|
28
|
+
* @param {number} value
|
|
29
|
+
* @param {EUnit} unit
|
|
30
|
+
* @param {number} exchangeRate
|
|
31
|
+
* @param {string} currency
|
|
32
|
+
*/
|
|
33
|
+
export const convertToSats = (
|
|
34
|
+
value: number | string,
|
|
35
|
+
unit: EUnit,
|
|
36
|
+
exchangeRate: number,
|
|
37
|
+
currency = 'EUR'
|
|
38
|
+
): number => {
|
|
39
|
+
const amount = Number(value);
|
|
40
|
+
|
|
41
|
+
if (unit === EUnit.BTC) {
|
|
42
|
+
return btcToSats(amount);
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
if (unit === EUnit.fiat) {
|
|
46
|
+
return fiatToBitcoinUnit({
|
|
47
|
+
fiatValue: amount,
|
|
48
|
+
unit: EUnit.satoshi,
|
|
49
|
+
exchangeRate,
|
|
50
|
+
currency
|
|
51
|
+
});
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
return amount;
|
|
55
|
+
};
|
|
56
|
+
|
|
57
|
+
/**
|
|
58
|
+
* Converts a fiat value to a bitcoin unit.
|
|
59
|
+
* @param {string | number} fiatValue
|
|
60
|
+
* @param {number} exchangeRate
|
|
61
|
+
* @param {string} currency
|
|
62
|
+
* @param {EUnit} unit
|
|
63
|
+
* @returns {number}
|
|
64
|
+
*/
|
|
65
|
+
export const fiatToBitcoinUnit = ({
|
|
66
|
+
fiatValue,
|
|
67
|
+
exchangeRate,
|
|
68
|
+
currency,
|
|
69
|
+
unit
|
|
70
|
+
}: {
|
|
71
|
+
fiatValue: string | number;
|
|
72
|
+
exchangeRate: number;
|
|
73
|
+
currency: string;
|
|
74
|
+
unit: EUnit;
|
|
75
|
+
}): number => {
|
|
76
|
+
try {
|
|
77
|
+
// this throws if exchangeRate is 0
|
|
78
|
+
bitcoinUnits.setFiat(currency, exchangeRate);
|
|
79
|
+
const value = bitcoinUnits(Number(fiatValue), currency)
|
|
80
|
+
.to(unit)
|
|
81
|
+
.value()
|
|
82
|
+
.toFixed(unit === EUnit.satoshi ? 0 : 8); // satoshi cannot be a fractional number
|
|
83
|
+
|
|
84
|
+
return Number(value);
|
|
85
|
+
} catch {
|
|
86
|
+
return 0;
|
|
87
|
+
}
|
|
88
|
+
};
|
|
@@ -0,0 +1,171 @@
|
|
|
1
|
+
import {
|
|
2
|
+
EAddressType,
|
|
3
|
+
EAvailableNetworks,
|
|
4
|
+
IKeyDerivationPath,
|
|
5
|
+
TKeyDerivationAccount,
|
|
6
|
+
TKeyDerivationChange,
|
|
7
|
+
TKeyDerivationCoinType,
|
|
8
|
+
TKeyDerivationPurpose
|
|
9
|
+
} from '../types';
|
|
10
|
+
import { addressTypes } from '../shapes';
|
|
11
|
+
import { err, ok, Result } from './result';
|
|
12
|
+
|
|
13
|
+
/**
|
|
14
|
+
* Parses a key derivation path in string format Ex: "m/84'/0'/0'/0/0" and returns IKeyDerivationPath.
|
|
15
|
+
* @param {string} keyDerivationPath
|
|
16
|
+
* @param {TKeyDerivationPurpose | string} [purpose]
|
|
17
|
+
* @param {boolean} [changeAddress]
|
|
18
|
+
* @param {string} [index]
|
|
19
|
+
* @param {TAvailableNetworks} [network]
|
|
20
|
+
* @returns {Result<IKeyDerivationPath>}
|
|
21
|
+
*/
|
|
22
|
+
export const getKeyDerivationPathObject = ({
|
|
23
|
+
path = '',
|
|
24
|
+
purpose,
|
|
25
|
+
changeAddress,
|
|
26
|
+
index,
|
|
27
|
+
network
|
|
28
|
+
}: {
|
|
29
|
+
path: string;
|
|
30
|
+
purpose?: TKeyDerivationPurpose;
|
|
31
|
+
changeAddress?: boolean;
|
|
32
|
+
index?: string;
|
|
33
|
+
network: EAvailableNetworks;
|
|
34
|
+
}): Result<IKeyDerivationPath> => {
|
|
35
|
+
try {
|
|
36
|
+
const parsedPath = path.replace(/'/g, '').split('/');
|
|
37
|
+
|
|
38
|
+
if (!purpose) {
|
|
39
|
+
purpose = parsedPath[1] as TKeyDerivationPurpose;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
let coinType = parsedPath[2] as TKeyDerivationCoinType;
|
|
43
|
+
if (network) {
|
|
44
|
+
coinType =
|
|
45
|
+
network.toLocaleLowerCase() === EAvailableNetworks.bitcoin ? '0' : '1';
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
const account = parsedPath[3] as TKeyDerivationAccount;
|
|
49
|
+
|
|
50
|
+
let change = parsedPath[4] as TKeyDerivationChange;
|
|
51
|
+
if (changeAddress !== undefined) {
|
|
52
|
+
change = changeAddress ? '1' : '0';
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
if (!index) {
|
|
56
|
+
index = parsedPath[5];
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
return ok({
|
|
60
|
+
purpose,
|
|
61
|
+
coinType,
|
|
62
|
+
account,
|
|
63
|
+
change,
|
|
64
|
+
index
|
|
65
|
+
});
|
|
66
|
+
} catch (e) {
|
|
67
|
+
return err(e);
|
|
68
|
+
}
|
|
69
|
+
};
|
|
70
|
+
|
|
71
|
+
/**
|
|
72
|
+
* Parses a key derivation path object and returns it in string format. Ex: "m/84'/0'/0'/0/0"
|
|
73
|
+
* @param {IKeyDerivationPath} path
|
|
74
|
+
* @param {TKeyDerivationPurpose | string} [purpose]
|
|
75
|
+
* @param {boolean} [changeAddress]
|
|
76
|
+
* @param {number} [accountType]
|
|
77
|
+
* @param {string} [addressIndex]
|
|
78
|
+
* @returns {Result<string>}
|
|
79
|
+
*/
|
|
80
|
+
export const getKeyDerivationPathString = ({
|
|
81
|
+
addressType = EAddressType.p2wpkh,
|
|
82
|
+
path,
|
|
83
|
+
purpose,
|
|
84
|
+
accountType,
|
|
85
|
+
changeAddress = false,
|
|
86
|
+
index = '0',
|
|
87
|
+
network
|
|
88
|
+
}: {
|
|
89
|
+
addressType: EAddressType;
|
|
90
|
+
path?: IKeyDerivationPath;
|
|
91
|
+
purpose?: TKeyDerivationPurpose;
|
|
92
|
+
accountType?: string | number;
|
|
93
|
+
changeAddress?: boolean;
|
|
94
|
+
index?: string | number;
|
|
95
|
+
network: EAvailableNetworks;
|
|
96
|
+
}): Result<string> => {
|
|
97
|
+
try {
|
|
98
|
+
if (!path) {
|
|
99
|
+
// Get default path object for the network and set it from there.
|
|
100
|
+
const str = addressTypes[addressType].path;
|
|
101
|
+
const res = getKeyDerivationPathObject({ path: str, network });
|
|
102
|
+
if (res.isErr()) {
|
|
103
|
+
return err(res.error.message);
|
|
104
|
+
}
|
|
105
|
+
path = res.value;
|
|
106
|
+
}
|
|
107
|
+
//Specifically specifying purpose will override the default accountType purpose value.
|
|
108
|
+
if (purpose !== undefined) {
|
|
109
|
+
path.purpose = purpose;
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
path.coinType =
|
|
113
|
+
network.toLocaleLowerCase() === EAvailableNetworks.bitcoin ? '0' : '1';
|
|
114
|
+
|
|
115
|
+
if (accountType !== undefined) {
|
|
116
|
+
if (typeof accountType === 'number') {
|
|
117
|
+
path.account = String(accountType);
|
|
118
|
+
}
|
|
119
|
+
path.account =
|
|
120
|
+
typeof accountType === 'number' ? String(accountType) : accountType;
|
|
121
|
+
} else {
|
|
122
|
+
path.account = '0';
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
path.change = changeAddress ? '1' : '0';
|
|
126
|
+
|
|
127
|
+
if (!index) {
|
|
128
|
+
index = '0';
|
|
129
|
+
}
|
|
130
|
+
if (typeof index === 'number') {
|
|
131
|
+
index = String(index);
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
return ok(
|
|
135
|
+
`m/${path.purpose}'/${path.coinType}'/${path.account}'/${path.change}/${index}`
|
|
136
|
+
);
|
|
137
|
+
} catch (e) {
|
|
138
|
+
return err(e);
|
|
139
|
+
}
|
|
140
|
+
};
|
|
141
|
+
|
|
142
|
+
/**
|
|
143
|
+
* Returns the address type from the specified derivation path.
|
|
144
|
+
* @param {string | IKeyDerivationPath} path
|
|
145
|
+
* @returns {Result<EAddressType>}
|
|
146
|
+
*/
|
|
147
|
+
export const getAddressTypeFromPath = (
|
|
148
|
+
path: string | IKeyDerivationPath
|
|
149
|
+
): Result<EAddressType> => {
|
|
150
|
+
try {
|
|
151
|
+
let purpose;
|
|
152
|
+
if (typeof path === 'object') {
|
|
153
|
+
purpose = path.purpose;
|
|
154
|
+
} else if (typeof path === 'string') {
|
|
155
|
+
const parsedPathString = path.replace(/'/g, '').split('/');
|
|
156
|
+
purpose = parsedPathString[1];
|
|
157
|
+
}
|
|
158
|
+
switch (purpose) {
|
|
159
|
+
case '44':
|
|
160
|
+
return ok(EAddressType.p2pkh);
|
|
161
|
+
case '49':
|
|
162
|
+
return ok(EAddressType.p2sh);
|
|
163
|
+
case '84':
|
|
164
|
+
return ok(EAddressType.p2wpkh);
|
|
165
|
+
default:
|
|
166
|
+
return err('Invalid path');
|
|
167
|
+
}
|
|
168
|
+
} catch (e) {
|
|
169
|
+
return err(e);
|
|
170
|
+
}
|
|
171
|
+
};
|
|
@@ -0,0 +1,188 @@
|
|
|
1
|
+
import * as electrum from 'rn-electrum-client/helpers';
|
|
2
|
+
import { err, ok, Result } from './result';
|
|
3
|
+
|
|
4
|
+
import {
|
|
5
|
+
EAvailableNetworks,
|
|
6
|
+
ElectrumConnectionPubSub,
|
|
7
|
+
ElectrumConnectionSubscription,
|
|
8
|
+
IFormattedPeerData,
|
|
9
|
+
TProtocol
|
|
10
|
+
} from '../types';
|
|
11
|
+
import * as hardcodedPeers from 'rn-electrum-client/helpers/peers.json';
|
|
12
|
+
|
|
13
|
+
const POLLING_INTERVAL = 1000 * 20;
|
|
14
|
+
export const defaultElectrumPorts = ['51002', '50002', '51001', '50001'];
|
|
15
|
+
|
|
16
|
+
/**
|
|
17
|
+
* Returns the default port for the given network and protocol.
|
|
18
|
+
* @param {EAvailableNetworks} [selectedNetwork]
|
|
19
|
+
* @param {string} [protocol]
|
|
20
|
+
* @returns {number}
|
|
21
|
+
*/
|
|
22
|
+
export const getDefaultPort = (
|
|
23
|
+
selectedNetwork: EAvailableNetworks,
|
|
24
|
+
protocol: TProtocol
|
|
25
|
+
): number => {
|
|
26
|
+
if (protocol === 'ssl') {
|
|
27
|
+
return selectedNetwork === 'testnet' ? 51002 : 50002;
|
|
28
|
+
} else {
|
|
29
|
+
return selectedNetwork === 'testnet' ? 51001 : 50001;
|
|
30
|
+
}
|
|
31
|
+
};
|
|
32
|
+
|
|
33
|
+
/**
|
|
34
|
+
* Returns the protocol for the given network and default port.
|
|
35
|
+
* @param {string} [port]
|
|
36
|
+
* @param {EAvailableNetworks} [network]
|
|
37
|
+
* @returns {TProtocol | undefined}
|
|
38
|
+
*/
|
|
39
|
+
export const getProtocolForPort = (
|
|
40
|
+
port: string,
|
|
41
|
+
network: EAvailableNetworks
|
|
42
|
+
): TProtocol | undefined => {
|
|
43
|
+
if (port === '443') {
|
|
44
|
+
return 'ssl';
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
if (network === 'testnet') {
|
|
48
|
+
return port === '51002' ? 'ssl' : 'tcp';
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
return port === '50002' ? 'ssl' : 'tcp';
|
|
52
|
+
};
|
|
53
|
+
|
|
54
|
+
/**
|
|
55
|
+
* Formats the peer data response from an Electrum server.
|
|
56
|
+
* @param {[string, string, [string, string, string]]} data
|
|
57
|
+
* @returns Result<IFormattedPeerData>
|
|
58
|
+
*/
|
|
59
|
+
export const formatPeerData = (
|
|
60
|
+
data: [string, string, [string, string, string]]
|
|
61
|
+
): Result<IFormattedPeerData> => {
|
|
62
|
+
try {
|
|
63
|
+
if (!data) {
|
|
64
|
+
return err('No data provided.');
|
|
65
|
+
}
|
|
66
|
+
if (data?.length !== 3) {
|
|
67
|
+
return err('Invalid peer data');
|
|
68
|
+
}
|
|
69
|
+
if (data[2]?.length < 2) {
|
|
70
|
+
return err('Invalid peer data');
|
|
71
|
+
}
|
|
72
|
+
const [ip, host, ports] = data;
|
|
73
|
+
const [version, ssl, tcp] = ports;
|
|
74
|
+
return ok({
|
|
75
|
+
ip,
|
|
76
|
+
host,
|
|
77
|
+
version,
|
|
78
|
+
ssl,
|
|
79
|
+
tcp
|
|
80
|
+
});
|
|
81
|
+
} catch (e) {
|
|
82
|
+
if (typeof e === 'string' || e instanceof Error) {
|
|
83
|
+
return err(e);
|
|
84
|
+
}
|
|
85
|
+
return err('Unable to format peer data.');
|
|
86
|
+
}
|
|
87
|
+
};
|
|
88
|
+
|
|
89
|
+
/**
|
|
90
|
+
* Returns an array of peers.
|
|
91
|
+
* If unable to acquire peers from an Electrum server the method will default to the hardcoded peers in peers.json.
|
|
92
|
+
* @param {EAvailableNetworks} [selectedNetwork]
|
|
93
|
+
* @returns Promise<Result<IFormattedPeerData[]>>
|
|
94
|
+
*/
|
|
95
|
+
export const getPeers = async ({
|
|
96
|
+
selectedNetwork
|
|
97
|
+
}: {
|
|
98
|
+
selectedNetwork: EAvailableNetworks;
|
|
99
|
+
}): Promise<Result<IFormattedPeerData[]>> => {
|
|
100
|
+
try {
|
|
101
|
+
const response = await electrum.getPeers({ network: selectedNetwork });
|
|
102
|
+
if (!response.error) {
|
|
103
|
+
// Return an array of peers provided by the currently connected electrum server.
|
|
104
|
+
const peers: IFormattedPeerData[] = [];
|
|
105
|
+
await Promise.all(
|
|
106
|
+
response.data.map(async (peer) => {
|
|
107
|
+
const formattedPeer = await formatPeerData(peer);
|
|
108
|
+
if (formattedPeer.isOk()) {
|
|
109
|
+
peers.push(formattedPeer.value);
|
|
110
|
+
}
|
|
111
|
+
})
|
|
112
|
+
);
|
|
113
|
+
if (peers?.length > 0) {
|
|
114
|
+
return ok(peers);
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
// No peers available grab hardcoded peers instead.
|
|
118
|
+
return ok(hardcodedPeers[selectedNetwork]);
|
|
119
|
+
} catch (e) {
|
|
120
|
+
if (typeof e === 'string' || e instanceof Error) {
|
|
121
|
+
return err(e);
|
|
122
|
+
}
|
|
123
|
+
return err('Unable to get peers.');
|
|
124
|
+
}
|
|
125
|
+
};
|
|
126
|
+
|
|
127
|
+
/**
|
|
128
|
+
* Background task that checks the connection to the Electrum server with a PubSub
|
|
129
|
+
* If connection was lost this will try to reconnect in the specified interval
|
|
130
|
+
* @param {() => Result<null>} [connectToElectrum]
|
|
131
|
+
* @returns {ElectrumConnectionPubSub}
|
|
132
|
+
*/
|
|
133
|
+
export const electrumConnection = ((
|
|
134
|
+
connectToElectrum?: () => Result<null>
|
|
135
|
+
): ElectrumConnectionPubSub => {
|
|
136
|
+
const subscribers: Set<(isConnected: boolean) => void> = new Set();
|
|
137
|
+
let latestState: boolean | null = null;
|
|
138
|
+
|
|
139
|
+
setInterval(async () => {
|
|
140
|
+
try {
|
|
141
|
+
const { error } = await electrum.pingServer();
|
|
142
|
+
|
|
143
|
+
if (error) {
|
|
144
|
+
if (connectToElectrum) {
|
|
145
|
+
console.log('Connection to Electrum Server lost, reconnecting...');
|
|
146
|
+
const response = await connectToElectrum();
|
|
147
|
+
|
|
148
|
+
if (response.isErr()) {
|
|
149
|
+
electrumConnection.publish(false);
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
} else {
|
|
153
|
+
electrumConnection.publish(true);
|
|
154
|
+
}
|
|
155
|
+
} catch (e) {
|
|
156
|
+
console.error(e);
|
|
157
|
+
}
|
|
158
|
+
}, POLLING_INTERVAL);
|
|
159
|
+
|
|
160
|
+
const publish = (isConnected: boolean): void => {
|
|
161
|
+
// Skip if no subscribers
|
|
162
|
+
if (subscribers.size === 0) {
|
|
163
|
+
return;
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
// Skip if state hasn't changed
|
|
167
|
+
if (latestState === isConnected) {
|
|
168
|
+
return;
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
latestState = isConnected;
|
|
172
|
+
subscribers.forEach((callback) => callback(isConnected));
|
|
173
|
+
};
|
|
174
|
+
|
|
175
|
+
const subscribe = (
|
|
176
|
+
callback: (isConnected: boolean) => void
|
|
177
|
+
): ElectrumConnectionSubscription => {
|
|
178
|
+
subscribers.add(callback);
|
|
179
|
+
|
|
180
|
+
return {
|
|
181
|
+
remove: (): void => {
|
|
182
|
+
subscribers.delete(callback);
|
|
183
|
+
}
|
|
184
|
+
};
|
|
185
|
+
};
|
|
186
|
+
|
|
187
|
+
return { publish, subscribe };
|
|
188
|
+
})();
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
import { ok, err, Result } from './result';
|
|
2
|
+
import { BLOCKTANK_HOST } from '../wallet/constants';
|
|
3
|
+
import { IExchangeRates } from '../types';
|
|
4
|
+
|
|
5
|
+
export const mostUsedExchangeTickers = {
|
|
6
|
+
USD: {
|
|
7
|
+
currencySymbol: '$',
|
|
8
|
+
quote: 'USD',
|
|
9
|
+
quoteName: 'US Dollar'
|
|
10
|
+
},
|
|
11
|
+
GBP: {
|
|
12
|
+
currencySymbol: '£',
|
|
13
|
+
quote: 'GBP',
|
|
14
|
+
quoteName: 'Great British Pound'
|
|
15
|
+
},
|
|
16
|
+
CAD: {
|
|
17
|
+
currencySymbol: '$',
|
|
18
|
+
quote: 'CAD',
|
|
19
|
+
quoteName: 'Canadian Dollar'
|
|
20
|
+
},
|
|
21
|
+
CNY: {
|
|
22
|
+
currencySymbol: '¥',
|
|
23
|
+
quote: 'CNY',
|
|
24
|
+
quoteName: 'Chinese Yuan Renminbi'
|
|
25
|
+
},
|
|
26
|
+
EUR: { currencySymbol: '€', quote: 'EUR', quoteName: 'Euro' }
|
|
27
|
+
};
|
|
28
|
+
|
|
29
|
+
type TTicker = {
|
|
30
|
+
symbol: string;
|
|
31
|
+
lastPrice: string;
|
|
32
|
+
base: string;
|
|
33
|
+
baseName: string;
|
|
34
|
+
quote: string;
|
|
35
|
+
quoteName: string;
|
|
36
|
+
currencySymbol: string;
|
|
37
|
+
currencyFlag: string;
|
|
38
|
+
lastUpdatedAt: number;
|
|
39
|
+
};
|
|
40
|
+
|
|
41
|
+
/**
|
|
42
|
+
* Returns the exchange rate for the given currency
|
|
43
|
+
* @returns {Promise<Result<IExchangeRates>>}
|
|
44
|
+
*/
|
|
45
|
+
export const getExchangeRates = async (): Promise<Result<IExchangeRates>> => {
|
|
46
|
+
try {
|
|
47
|
+
const response = await fetch(`${BLOCKTANK_HOST}/fx/rates/btc`);
|
|
48
|
+
const { tickers } = await response.json();
|
|
49
|
+
|
|
50
|
+
const rates: IExchangeRates = tickers.reduce(
|
|
51
|
+
(acc: IExchangeRates, ticker: TTicker) => {
|
|
52
|
+
return {
|
|
53
|
+
...acc,
|
|
54
|
+
[ticker.quote]: {
|
|
55
|
+
currencySymbol: ticker.currencySymbol,
|
|
56
|
+
quote: ticker.quote,
|
|
57
|
+
quoteName: ticker.quoteName,
|
|
58
|
+
rate: Math.round(Number(ticker.lastPrice) * 100) / 100,
|
|
59
|
+
lastUpdatedAt: ticker.lastUpdatedAt
|
|
60
|
+
}
|
|
61
|
+
};
|
|
62
|
+
},
|
|
63
|
+
{}
|
|
64
|
+
);
|
|
65
|
+
|
|
66
|
+
return ok(rates);
|
|
67
|
+
} catch (e) {
|
|
68
|
+
return err(e);
|
|
69
|
+
}
|
|
70
|
+
};
|
|
@@ -0,0 +1,191 @@
|
|
|
1
|
+
import { EAddressType, EAvailableNetworks, IKeyDerivationPath } from '../types';
|
|
2
|
+
import { address as bitcoinJSAddress, Network, networks } from 'bitcoinjs-lib';
|
|
3
|
+
import bip39 = require('bip39');
|
|
4
|
+
import * as bitcoin from 'bitcoinjs-lib';
|
|
5
|
+
import { availableNetworks, isValidBech32mEncodedString } from './wallet';
|
|
6
|
+
import { err, ok, Result } from './result';
|
|
7
|
+
import { addressTypes } from '../shapes';
|
|
8
|
+
import { getKeyDerivationPathObject } from './derivation-path';
|
|
9
|
+
|
|
10
|
+
/**
|
|
11
|
+
* Get address for a given scriptPubKey.
|
|
12
|
+
* @param scriptPubKey
|
|
13
|
+
* @param selectedNetwork
|
|
14
|
+
* @returns {string}
|
|
15
|
+
*/
|
|
16
|
+
export const getAddressFromScriptPubKey = (
|
|
17
|
+
scriptPubKey: string,
|
|
18
|
+
selectedNetwork: EAvailableNetworks
|
|
19
|
+
): string => {
|
|
20
|
+
const network = networks[selectedNetwork];
|
|
21
|
+
return bitcoin.address.fromOutputScript(
|
|
22
|
+
Buffer.from(scriptPubKey, 'hex'),
|
|
23
|
+
network
|
|
24
|
+
);
|
|
25
|
+
};
|
|
26
|
+
|
|
27
|
+
/**
|
|
28
|
+
* Get sha256 hash of a given string.
|
|
29
|
+
* @param {string} str
|
|
30
|
+
* @returns {string}
|
|
31
|
+
*/
|
|
32
|
+
export const getSha256 = (str: string): string => {
|
|
33
|
+
const buffer = Buffer.from(str, 'utf8');
|
|
34
|
+
const hash = bitcoin.crypto.sha256(buffer);
|
|
35
|
+
return hash.toString('hex');
|
|
36
|
+
};
|
|
37
|
+
|
|
38
|
+
/**
|
|
39
|
+
* Validate address for a given network.
|
|
40
|
+
* If no address is provided, it will attempt to validate the address for all available networks.
|
|
41
|
+
* @param {string} address
|
|
42
|
+
* @param {EAvailableNetworks} network
|
|
43
|
+
* @returns {{isValid: boolean, network: EAvailableNetworks}}
|
|
44
|
+
*/
|
|
45
|
+
export const validateAddress = ({
|
|
46
|
+
address,
|
|
47
|
+
network
|
|
48
|
+
}: {
|
|
49
|
+
address: string;
|
|
50
|
+
network?: EAvailableNetworks;
|
|
51
|
+
}): {
|
|
52
|
+
isValid: boolean;
|
|
53
|
+
network: EAvailableNetworks;
|
|
54
|
+
} => {
|
|
55
|
+
try {
|
|
56
|
+
//Validate address for all available networks
|
|
57
|
+
let isValid = false;
|
|
58
|
+
const availableNetworksList = availableNetworks();
|
|
59
|
+
|
|
60
|
+
//Validate address for a specific network
|
|
61
|
+
if (network !== undefined) {
|
|
62
|
+
try {
|
|
63
|
+
bitcoinJSAddress.toOutputScript(address, networks[network]);
|
|
64
|
+
return { isValid: true, network };
|
|
65
|
+
} catch {
|
|
66
|
+
// In the event the normal check fails, determine if this is a taproot address.
|
|
67
|
+
const taprootRes = isValidBech32mEncodedString(address);
|
|
68
|
+
if (taprootRes.isValid && taprootRes.network === network) {
|
|
69
|
+
return { isValid: taprootRes.isValid, network: taprootRes.network };
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
return { isValid: false, network };
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
for (let i = 0; i < availableNetworksList.length; i++) {
|
|
76
|
+
const validateRes = validateAddress({
|
|
77
|
+
address,
|
|
78
|
+
network: availableNetworksList[i]
|
|
79
|
+
});
|
|
80
|
+
if (validateRes.isValid) {
|
|
81
|
+
isValid = validateRes.isValid;
|
|
82
|
+
network = validateRes.network;
|
|
83
|
+
break;
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
return { isValid, network: network ?? EAvailableNetworks.bitcoin };
|
|
87
|
+
} catch {
|
|
88
|
+
return { isValid: false, network: EAvailableNetworks.bitcoin };
|
|
89
|
+
}
|
|
90
|
+
};
|
|
91
|
+
|
|
92
|
+
/**
|
|
93
|
+
* Returns the derivation path object for the specified addressType and network.
|
|
94
|
+
* @param {EAddressType} addressType
|
|
95
|
+
* @param {EAvailableNetworks} [selectedNetwork]
|
|
96
|
+
* @returns Result<IKeyDerivationPath>
|
|
97
|
+
*/
|
|
98
|
+
export const getKeyDerivationPath = ({
|
|
99
|
+
addressType,
|
|
100
|
+
network
|
|
101
|
+
}: {
|
|
102
|
+
addressType: EAddressType;
|
|
103
|
+
network: EAvailableNetworks;
|
|
104
|
+
}): Result<IKeyDerivationPath> => {
|
|
105
|
+
try {
|
|
106
|
+
const keyDerivationPathResponse = getKeyDerivationPathObject({
|
|
107
|
+
network,
|
|
108
|
+
path: addressTypes[addressType].path
|
|
109
|
+
});
|
|
110
|
+
if (keyDerivationPathResponse.isErr()) {
|
|
111
|
+
return err(keyDerivationPathResponse.error.message);
|
|
112
|
+
}
|
|
113
|
+
return ok(keyDerivationPathResponse.value);
|
|
114
|
+
} catch (e) {
|
|
115
|
+
return err(e);
|
|
116
|
+
}
|
|
117
|
+
};
|
|
118
|
+
|
|
119
|
+
/**
|
|
120
|
+
* Get scriptHash for a given address
|
|
121
|
+
* @param {string} address
|
|
122
|
+
* @param {EAvailableNetworks} network
|
|
123
|
+
* @returns {string}
|
|
124
|
+
*/
|
|
125
|
+
export const getScriptHash = ({
|
|
126
|
+
address,
|
|
127
|
+
network
|
|
128
|
+
}: {
|
|
129
|
+
address: string;
|
|
130
|
+
network: EAvailableNetworks;
|
|
131
|
+
}): string => {
|
|
132
|
+
try {
|
|
133
|
+
const _network: Network = bitcoin.networks[network];
|
|
134
|
+
const script = bitcoin.address.toOutputScript(address, _network);
|
|
135
|
+
const hash = bitcoin.crypto.sha256(script);
|
|
136
|
+
const reversedHash = Buffer.from(hash.reverse());
|
|
137
|
+
return reversedHash.toString('hex');
|
|
138
|
+
} catch {
|
|
139
|
+
return '';
|
|
140
|
+
}
|
|
141
|
+
};
|
|
142
|
+
|
|
143
|
+
/**
|
|
144
|
+
* Extends bip39's generateMnemonic function.
|
|
145
|
+
* @param {number} [strength]
|
|
146
|
+
* @param {(size: number) => Buffer} [rng]
|
|
147
|
+
* @param {string[]} [wordlist]
|
|
148
|
+
* @returns {string}
|
|
149
|
+
*/
|
|
150
|
+
export const generateMnemonic = (
|
|
151
|
+
strength?: number,
|
|
152
|
+
rng?: (size: number) => Buffer,
|
|
153
|
+
wordlist?: string[]
|
|
154
|
+
): string => {
|
|
155
|
+
return bip39.generateMnemonic(strength, rng, wordlist);
|
|
156
|
+
};
|
|
157
|
+
|
|
158
|
+
/**
|
|
159
|
+
* Attempts to validate the provided mnemonic.
|
|
160
|
+
* @param {string} mnemonic
|
|
161
|
+
* @returns {boolean}
|
|
162
|
+
*/
|
|
163
|
+
export const validateMnemonic = (mnemonic = ''): boolean => {
|
|
164
|
+
try {
|
|
165
|
+
return bip39.validateMnemonic(mnemonic);
|
|
166
|
+
} catch {
|
|
167
|
+
return false;
|
|
168
|
+
}
|
|
169
|
+
};
|
|
170
|
+
|
|
171
|
+
/**
|
|
172
|
+
* Determines if the two objects passed as params match.
|
|
173
|
+
* @param obj1
|
|
174
|
+
* @param obj2
|
|
175
|
+
* @returns boolean
|
|
176
|
+
*/
|
|
177
|
+
export const objectsMatch = (obj1, obj2): boolean => {
|
|
178
|
+
if (!obj1 || !obj2) {
|
|
179
|
+
return false;
|
|
180
|
+
}
|
|
181
|
+
const obj1Length = Object.keys(obj1).length;
|
|
182
|
+
const obj2Length = Object.keys(obj2).length;
|
|
183
|
+
|
|
184
|
+
if (obj1Length === obj2Length) {
|
|
185
|
+
return Object.keys(obj1).every(
|
|
186
|
+
(key) => key in obj2 && obj2[key] === obj1[key]
|
|
187
|
+
);
|
|
188
|
+
} else {
|
|
189
|
+
return false;
|
|
190
|
+
}
|
|
191
|
+
};
|