Resolve "WIP: UTXO Selection and Storage"
This commit is contained in:
@@ -0,0 +1,605 @@
|
||||
import {
|
||||
Address,
|
||||
BlockHeader,
|
||||
Bytes,
|
||||
encodeExtendedJson,
|
||||
decodeExtendedJson,
|
||||
Hasher,
|
||||
HDPrivateNode,
|
||||
HDPublicNode,
|
||||
Mnemonic,
|
||||
PrivateKey,
|
||||
PublicKey,
|
||||
Satoshis,
|
||||
Script,
|
||||
Transaction,
|
||||
} from '@xocash/primitives';
|
||||
|
||||
export const address = {
|
||||
from: [
|
||||
{
|
||||
label: 'From',
|
||||
inputs: ['CashAddr or Legacy Address'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Address.from(...args),
|
||||
extendedInput: true,
|
||||
},
|
||||
{
|
||||
label: 'From CashAddr',
|
||||
inputs: ['CashAddr'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Address.fromCashAddr(...args),
|
||||
extendedInput: true,
|
||||
},
|
||||
{
|
||||
label: 'From Legacy',
|
||||
inputs: ['Legacy Address'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Address.fromLegacy(...args),
|
||||
extendedInput: true,
|
||||
},
|
||||
{
|
||||
label: 'From Redeem Script Hex (P2SH20)',
|
||||
inputs: ['RedeemScript Hex'],
|
||||
models: [''],
|
||||
callback: (args: [string]) =>
|
||||
Address.fromRedeemScriptHex(...args, 'P2SH20'),
|
||||
extendedInput: true,
|
||||
},
|
||||
{
|
||||
label: 'From Redeem Script Hex (P2SH32)',
|
||||
inputs: ['RedeemScript Hex'],
|
||||
models: [''],
|
||||
callback: (args: [string]) =>
|
||||
Address.fromRedeemScriptHex(...args, 'P2SH32'),
|
||||
extendedInput: true,
|
||||
},
|
||||
{
|
||||
label: 'From Lockscript Hex',
|
||||
inputs: ['Lockscript Hex'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Address.fromLockscriptHex(...args),
|
||||
extendedInput: true,
|
||||
},
|
||||
{
|
||||
label: 'From Hash160 Hex',
|
||||
inputs: ['Hash160 Hex'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Address.fromHash160Hex(...args),
|
||||
extendedInput: true,
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'To CashAddr (mainnet)',
|
||||
callback: (address: Address) => address.toCashAddr('bitcoincash'),
|
||||
},
|
||||
{
|
||||
label: 'To CashAddr (testnet)',
|
||||
callback: (address: Address) => address.toCashAddr('bchtest'),
|
||||
},
|
||||
{
|
||||
label: 'To CashAddr (regtest)',
|
||||
callback: (address: Address) => address.toCashAddr('bchreg'),
|
||||
},
|
||||
{
|
||||
label: 'To TokenAware CashAddr (mainnet)',
|
||||
callback: (address: Address) => address.toTokenAddress('bitcoincash'),
|
||||
},
|
||||
{
|
||||
label: 'To TokenAware CashAddr (testnet)',
|
||||
callback: (address: Address) => address.toTokenAddress('bchtest'),
|
||||
},
|
||||
{
|
||||
label: 'To TokenAware CashAddr (regtest)',
|
||||
callback: (address: Address) => address.toTokenAddress('bchreg'),
|
||||
},
|
||||
{
|
||||
label: 'To Legacy',
|
||||
callback: (address: Address) => address.toLegacy(),
|
||||
},
|
||||
{
|
||||
label: 'To Hash160/RIPEMD Hex',
|
||||
callback: (address: Address) => address.toHash160Hex(),
|
||||
},
|
||||
{
|
||||
label: 'To Lockscript Hex',
|
||||
callback: (address: Address) => address.toLockscriptHex(),
|
||||
},
|
||||
{
|
||||
label: 'To Lockscript ASM',
|
||||
callback: (address: Address) => address.toLockscriptAsm(),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
export const blockHeader = {
|
||||
from: [
|
||||
{
|
||||
label: 'From Hex',
|
||||
inputs: ['UTF-8'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => BlockHeader.fromHex(...args),
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'To Raw',
|
||||
callback: (blockHeader: BlockHeader) => blockHeader.toRaw(),
|
||||
},
|
||||
{
|
||||
label: 'Version',
|
||||
callback: (blockHeader: BlockHeader) => blockHeader.getVersion(),
|
||||
},
|
||||
{
|
||||
label: 'Previous Block Hash',
|
||||
callback: (blockHeader: BlockHeader) =>
|
||||
blockHeader.getPreviousBlockHashHex(),
|
||||
},
|
||||
{
|
||||
label: 'Merkle Root',
|
||||
callback: (blockHeader: BlockHeader) => blockHeader.getMerkleRootHex(),
|
||||
},
|
||||
{
|
||||
label: 'Timestamp',
|
||||
callback: (blockHeader: BlockHeader) =>
|
||||
blockHeader.getTimestamp().toString(),
|
||||
},
|
||||
{
|
||||
label: 'Bits',
|
||||
callback: (blockHeader: BlockHeader) => blockHeader.getBits().toString(),
|
||||
},
|
||||
{
|
||||
label: 'Nonce',
|
||||
callback: (blockHeader: BlockHeader) => blockHeader.getNonce().toString(),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
export const bytes = {
|
||||
from: [
|
||||
{
|
||||
label: 'From Base64',
|
||||
inputs: ['Base64'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Bytes.fromBase64(...args),
|
||||
},
|
||||
{
|
||||
label: 'From Hex',
|
||||
inputs: ['Hex'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Bytes.fromHex(...args),
|
||||
},
|
||||
{
|
||||
label: 'From UTF-8',
|
||||
inputs: ['UTF-8'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Bytes.fromUtf8(...args),
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'To Base64',
|
||||
callback: (bytes: Bytes) => bytes.toBase64(),
|
||||
},
|
||||
{
|
||||
label: 'To Hex',
|
||||
callback: (bytes: Bytes) => bytes.toHex(),
|
||||
},
|
||||
{
|
||||
label: 'To UTF-8',
|
||||
callback: (bytes: Bytes) => bytes.toUtf8(),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
export const hasher = {
|
||||
from: [
|
||||
{
|
||||
label: 'From Hex',
|
||||
inputs: ['Hex'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Hasher.fromHex(...args),
|
||||
},
|
||||
{
|
||||
label: 'From Base64',
|
||||
inputs: ['Base64'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Hasher.fromBase64(...args),
|
||||
},
|
||||
{
|
||||
label: 'From UTF-8',
|
||||
inputs: ['UTF-8'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Hasher.fromUTF8(...args),
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'To Sha256 Hex',
|
||||
callback: (hasher: Hasher) => hasher.toSHA256Hex(),
|
||||
},
|
||||
{
|
||||
label: 'To RipeMD160 Hex',
|
||||
callback: (hasher: Hasher) => hasher.toRIPEMD160Hex(),
|
||||
},
|
||||
{
|
||||
label: 'To Hash160 Hex',
|
||||
callback: (hasher: Hasher) => hasher.toHash160Hex(),
|
||||
},
|
||||
{
|
||||
label: 'To Hash256 Hex',
|
||||
callback: (hasher: Hasher) => hasher.toHash256Hex(),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
export const hdPrivateNode = {
|
||||
from: [
|
||||
{
|
||||
label: 'Generate Random',
|
||||
inputs: ['Derivation Path'],
|
||||
models: ["m/44'/145'/0'/0/1"],
|
||||
callback: () => HDPrivateNode.generateRandom(),
|
||||
},
|
||||
{
|
||||
label: 'From Mnemonic',
|
||||
inputs: ['Mnemonic', 'Derivation Path'],
|
||||
models: ['', "m/44'/145'/0'/0/1"],
|
||||
callback: (args: [string]) => HDPrivateNode.fromMnemonic(...args),
|
||||
},
|
||||
{
|
||||
label: 'From XPriv Key',
|
||||
inputs: ['XPriv Key', 'Derivation Path'],
|
||||
models: ['', "m/44'/145'/0'/0/1"],
|
||||
callback: (args: [string]) => HDPrivateNode.fromXPriv(...args),
|
||||
},
|
||||
{
|
||||
label: 'From Raw',
|
||||
inputs: ['Raw (LibAuth Format/ExtJSON Encoded)'],
|
||||
models: [''],
|
||||
callback: (args: [string]) =>
|
||||
HDPrivateNode.fromRaw(decodeExtendedJson(args.join(''))),
|
||||
extendedInput: true,
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'To XPriv Key',
|
||||
callback: (hdPrivateNode: HDPrivateNode) => hdPrivateNode.toXPriv(),
|
||||
},
|
||||
{
|
||||
label: 'To String',
|
||||
callback: (hdPrivateNode: HDPrivateNode) => hdPrivateNode.toString(),
|
||||
},
|
||||
{
|
||||
label: 'To Raw (LibAuth Format/ExtJSON Encoded)',
|
||||
callback: (hdPrivateNode: HDPrivateNode) =>
|
||||
encodeExtendedJson(hdPrivateNode.toRaw(), 2),
|
||||
},
|
||||
{
|
||||
label: 'To XPub Key',
|
||||
callback: (hdPrivateNode: HDPrivateNode) =>
|
||||
hdPrivateNode.deriveHDPublicNode().toXPub(),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
export const hdPublicNode = {
|
||||
from: [
|
||||
{
|
||||
label: 'From XPub Key',
|
||||
inputs: ['XPub Key'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => HDPublicNode.fromXPub(...args),
|
||||
},
|
||||
{
|
||||
label: 'From Raw',
|
||||
inputs: ['Raw (LibAuth Format/ExtJSON Encoded)'],
|
||||
models: [''],
|
||||
callback: (args: [string]) =>
|
||||
HDPublicNode.fromRaw(decodeExtendedJson(args.join(''))),
|
||||
extendedInput: true,
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'To XPub Key',
|
||||
callback: (hdPublicNode: HDPublicNode) => hdPublicNode.toXPub(),
|
||||
},
|
||||
{
|
||||
label: 'To String',
|
||||
callback: (hdPublicNode: HDPublicNode) => hdPublicNode.toString(),
|
||||
},
|
||||
{
|
||||
label: 'To Raw (LibAuth Format/ExtJSON Encoded)',
|
||||
callback: (hdPublicNode: HDPublicNode) =>
|
||||
encodeExtendedJson(hdPublicNode.toRaw(), 2),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
export const mnemonic = {
|
||||
from: [
|
||||
{
|
||||
label: 'Generate Random',
|
||||
callback: () => Mnemonic.generateRandom(),
|
||||
},
|
||||
{
|
||||
label: 'From String',
|
||||
inputs: ['String'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Mnemonic.fromString(...args),
|
||||
extendedInput: true,
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'To String (without passphrase)',
|
||||
callback: (mnemonic: Mnemonic) => mnemonic.toString(false),
|
||||
},
|
||||
{
|
||||
label: 'To String (with passphrase)',
|
||||
callback: (mnemonic: Mnemonic) => mnemonic.toString(true),
|
||||
},
|
||||
{
|
||||
label: 'Words',
|
||||
callback: (mnemonic: Mnemonic) => mnemonic.toWords(),
|
||||
},
|
||||
{
|
||||
label: 'Passphrase',
|
||||
callback: (mnemonic: Mnemonic) => mnemonic.getPassphrase(),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
// TODO: Message Signing outputs. Maybe add an `extension` flag to the `to` that allows another input field and uses that to generate the outputs
|
||||
export const privateKey = {
|
||||
from: [
|
||||
{
|
||||
label: 'Generate Random',
|
||||
callback: () => PrivateKey.generateRandom(),
|
||||
},
|
||||
{
|
||||
label: 'From Hex',
|
||||
inputs: ['Hex'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => PrivateKey.fromHex(...args),
|
||||
},
|
||||
{
|
||||
label: 'From WIF',
|
||||
inputs: ['WIF'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => PrivateKey.fromWIF(...args),
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'To Hex',
|
||||
callback: (privateKey: PrivateKey) => privateKey.toHex(),
|
||||
},
|
||||
{
|
||||
label: 'To WIF',
|
||||
callback: (privateKey: PrivateKey) => privateKey.toWif(),
|
||||
},
|
||||
{
|
||||
label: 'To String',
|
||||
callback: (privateKey: PrivateKey) => privateKey.toString(),
|
||||
},
|
||||
{
|
||||
label: 'Derived Public Key (Hex)',
|
||||
callback: (privateKey: PrivateKey) =>
|
||||
privateKey.derivePublicKey().toString(),
|
||||
},
|
||||
{
|
||||
label: 'Derived BCH Address (CashAddr)',
|
||||
callback: (privateKey: PrivateKey) =>
|
||||
privateKey.derivePublicKey().deriveAddress().toCashAddr('bitcoincash'),
|
||||
},
|
||||
],
|
||||
methods: [
|
||||
{
|
||||
label: 'Sign Message (Schnorr)',
|
||||
inputs: ['UTF8'],
|
||||
models: ['Your text here'],
|
||||
callback: (privateKey: PrivateKey, args: [string]) =>
|
||||
Bytes.fromBytes(privateKey.signMessageSchnorr(...args)).toHex(),
|
||||
},
|
||||
{
|
||||
label: 'Sign Message (DER)',
|
||||
inputs: ['UTF8'],
|
||||
models: ['Your text here'],
|
||||
callback: (privateKey: PrivateKey, args: [string]) =>
|
||||
Bytes.fromBytes(privateKey.signMessageDER(...args)).toHex(),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
export const publicKey = {
|
||||
from: [
|
||||
{
|
||||
label: 'From Hex',
|
||||
inputs: ['Hex'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => PublicKey.fromHex(...args),
|
||||
},
|
||||
{
|
||||
label: 'From WIF',
|
||||
inputs: ['WIF'],
|
||||
models: [''],
|
||||
callback: (args: [string]) =>
|
||||
PrivateKey.fromWIF(...args).derivePublicKey(),
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'Derived Hash160 Hex',
|
||||
callback: (publicKey: PublicKey) => publicKey.deriveHash160Hex(),
|
||||
},
|
||||
{
|
||||
label: 'Derived Address',
|
||||
callback: (publicKey: PublicKey) =>
|
||||
publicKey.deriveAddress().toCashAddr(),
|
||||
},
|
||||
{
|
||||
label: 'To Hex',
|
||||
callback: (publicKey: PublicKey) => publicKey.toHex(),
|
||||
},
|
||||
{
|
||||
label: 'To String',
|
||||
callback: (publicKey: PublicKey) => publicKey.toString(),
|
||||
},
|
||||
],
|
||||
methods: [
|
||||
{
|
||||
label: 'Verify Message (Schnorr)',
|
||||
inputs: ['Message (UTF8)', 'Signature (Hex)'],
|
||||
models: ['Your text here'],
|
||||
callback: (publicKey: PublicKey, args: [string, string]) =>
|
||||
publicKey.verifyMessageSchnorr(...args).toString(),
|
||||
},
|
||||
{
|
||||
label: 'Verify Message (DER)',
|
||||
inputs: ['Message (UTF8)', 'Signature (Hex)'],
|
||||
models: ['Your text here'],
|
||||
callback: (publicKey: PublicKey, args: [string, string]) =>
|
||||
publicKey.verifyMessageDER(...args).toString(),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
export const satoshis = {
|
||||
from: [
|
||||
{
|
||||
label: 'From Sats',
|
||||
inputs: ['Sats'],
|
||||
models: [''],
|
||||
callback: (args: [number]) => Satoshis.fromSats(...args),
|
||||
},
|
||||
{
|
||||
label: 'From Bits',
|
||||
inputs: ['Bits'],
|
||||
models: [''],
|
||||
callback: (args: [number]) => Satoshis.fromBits(...args),
|
||||
},
|
||||
{
|
||||
label: 'From MBCH',
|
||||
inputs: ['MBCH'],
|
||||
models: [''],
|
||||
callback: (args: [number]) => Satoshis.fromMBCH(...args),
|
||||
},
|
||||
{
|
||||
label: 'From BCH',
|
||||
inputs: ['BCH'],
|
||||
models: [''],
|
||||
callback: (args: [number]) => Satoshis.fromBCH(...args),
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'To Sats',
|
||||
callback: (satoshis: Satoshis) => satoshis.toSats().toString(),
|
||||
},
|
||||
{
|
||||
label: 'To Bits',
|
||||
callback: (satoshis: Satoshis) => satoshis.toBits().toString(),
|
||||
},
|
||||
{
|
||||
label: 'To MBCH',
|
||||
callback: (satoshis: Satoshis) => satoshis.toMBCH().toString(),
|
||||
},
|
||||
{
|
||||
label: 'To BCH',
|
||||
callback: (satoshis: Satoshis) => satoshis.toBCH().toString(),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
export const script = {
|
||||
from: [
|
||||
{
|
||||
label: 'From ASM',
|
||||
inputs: ['ASM'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Script.fromASM(...args),
|
||||
},
|
||||
{
|
||||
label: 'From Hex',
|
||||
inputs: ['Hex'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Script.fromHex(...args),
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'To ASM',
|
||||
callback: (script: Script) => script.toASM(),
|
||||
},
|
||||
{
|
||||
label: 'To Hex',
|
||||
callback: (script: Script) => script.toHex(),
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
export const transaction = {
|
||||
from: [
|
||||
{
|
||||
label: 'From Hex',
|
||||
inputs: ['Hex'],
|
||||
models: [''],
|
||||
callback: (args: [string]) => Transaction.fromHex(...args),
|
||||
extendedInput: true,
|
||||
},
|
||||
{
|
||||
label: 'From Raw',
|
||||
inputs: ['Raw (LibAuth Format/ExtJSON Encoded)'],
|
||||
models: [''],
|
||||
callback: (args: [...string[]]) =>
|
||||
Transaction.fromRaw(decodeExtendedJson(args.join(''))),
|
||||
extendedInput: true,
|
||||
},
|
||||
],
|
||||
to: [
|
||||
{
|
||||
label: 'To Transaction Hash Hex',
|
||||
callback: (transaction: Transaction) => transaction.toHashHex(),
|
||||
},
|
||||
{
|
||||
label: 'To Raw (LibAuth Format/ExtJSON Encoded)',
|
||||
callback: (transaction: Transaction) =>
|
||||
encodeExtendedJson(transaction.toRaw(), 2),
|
||||
},
|
||||
{
|
||||
label: 'To Hex',
|
||||
callback: (transaction: Transaction) => transaction.toHex(),
|
||||
},
|
||||
{
|
||||
label: 'Version',
|
||||
callback: (transaction: Transaction) =>
|
||||
transaction.getVersion().toString(),
|
||||
},
|
||||
{
|
||||
label: 'Inputs',
|
||||
callback: (transaction: Transaction) => {
|
||||
return encodeExtendedJson(transaction.getInputs(), 2);
|
||||
},
|
||||
},
|
||||
{
|
||||
label: 'Outputs',
|
||||
callback: (transaction: Transaction) => {
|
||||
return encodeExtendedJson(transaction.getOutputs(), 2);
|
||||
},
|
||||
},
|
||||
{
|
||||
label: 'Locktime',
|
||||
callback: (transaction: Transaction) =>
|
||||
transaction.getLocktime().toString(),
|
||||
},
|
||||
{
|
||||
label: 'Is Coinbase',
|
||||
callback: (transaction: Transaction) =>
|
||||
transaction.isCoinbase().toString(),
|
||||
},
|
||||
],
|
||||
};
|
||||
Reference in New Issue
Block a user