Skip to content

Commit

Permalink
cleanups
Browse files Browse the repository at this point in the history
  • Loading branch information
wolverineks committed Feb 10, 2023
1 parent bda50e9 commit 4225e89
Show file tree
Hide file tree
Showing 18 changed files with 248 additions and 311 deletions.
39 changes: 1 addition & 38 deletions src/Send/SendScreen/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,14 +5,7 @@ import {IntlShape} from 'react-intl'

import {formatTokenAmount, formatTokenInteger, normalizeTokenAmount} from '../../legacy/format'
import {getCardanoNetworkConfigById, isHaskellShelleyNetwork} from '../../legacy/networks'
import {cardanoValueFromMultiToken} from '../../legacy/utils'
import {
AssetOverflowError,
CardanoMobile,
MultiToken,
NotEnoughMoneyToSendError,
YoroiWallet,
} from '../../yoroi-wallets'
import {AssetOverflowError, getMinAda, NotEnoughMoneyToSendError, YoroiWallet} from '../../yoroi-wallets'
import {DefaultAsset, Quantity, SendTokenList, Token, YoroiUnsignedTx} from '../../yoroi-wallets/types'
import {RawUtxo} from '../../yoroi-wallets/types/other'
import {Amounts, Quantities} from '../../yoroi-wallets/utils'
Expand All @@ -21,36 +14,6 @@ import type {AddressValidationErrors} from '../../yoroi-wallets/utils/validators
import {getUnstoppableDomainAddress, isReceiverAddressValid, validateAmount} from '../../yoroi-wallets/utils/validators'
import {amountInputErrorMessages, messages} from './strings'

export const getMinAda = async (selectedToken: Token, defaultAsset: DefaultAsset) => {
const networkConfig = getCardanoNetworkConfigById(defaultAsset.networkId)
const fakeAmount = new BigNumber('0') // amount doesn't matter for calculating min UTXO amount
const fakeMultitoken = new MultiToken(
[
{
identifier: defaultAsset.identifier,
networkId: defaultAsset.networkId,
amount: fakeAmount,
},
{
identifier: selectedToken.identifier,
networkId: selectedToken.networkId,
amount: fakeAmount,
},
],
{
defaultNetworkId: defaultAsset.networkId,
defaultIdentifier: defaultAsset.identifier,
},
)
const minAmount = await CardanoMobile.minAdaRequired(
await cardanoValueFromMultiToken(fakeMultitoken),
await CardanoMobile.BigNum.fromStr(networkConfig.MINIMUM_UTXO_VAL),
)
// if the user is sending a token, we need to make sure the resulting utxo
// has at least the minimum amount of ADA in it
return minAmount.toStr()
}

export const getTransactionData = async (
wallet: YoroiWallet,
address: string,
Expand Down
11 changes: 0 additions & 11 deletions src/legacy/ISignRequest.ts

This file was deleted.

54 changes: 1 addition & 53 deletions src/legacy/commonUtils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,13 +5,11 @@
* TODO: migrate here common utilities from Byron/util.js
*/

import {BigNumber} from 'bignumber.js'
import {generateMnemonic, mnemonicToEntropy} from 'bip39'
import cryptoRandomString from 'crypto-random-string'
import {randomBytes} from 'react-native-randombytes'

import {Cardano, CardanoMobile, DefaultTokenEntry} from '../yoroi-wallets'
import {MultiToken} from '../yoroi-wallets'
import {Cardano, CardanoMobile} from '../yoroi-wallets'
import {SendTokenList} from '../yoroi-wallets/types'
import type {WalletImplementationId} from '../yoroi-wallets/types/other'
import {DERIVATION_TYPES} from '../yoroi-wallets/types/other'
Expand Down Expand Up @@ -95,53 +93,3 @@ export const hasSendAllDefault = (tokens: SendTokenList): boolean => {
})
return defaultSendAll != null
}

/**
* Construct the list of what will be included in the tx output
*/
export const builtSendTokenList = (
defaultToken: DefaultTokenEntry,
tokens: SendTokenList,
utxos: Array<MultiToken>,
): MultiToken => {
const amount = new MultiToken([], defaultToken)

for (const token of tokens) {
if ((token as any).amount != null) {
// if we add a specific amount of a specific token to the output, just add it
amount.add({
amount: new BigNumber((token as any).amount),
identifier: token.token.identifier,
networkId: token.token.networkId,
})
} else if (token.token.isDefault) {
// if we add a non-specific amount of the default token
// sum amount values in the UTXO
const relatedUtxoSum = utxos.reduce((value, next) => value.plus(next.getDefaultEntry().amount), new BigNumber(0))
amount.add({
amount: relatedUtxoSum,
identifier: token.token.identifier,
networkId: token.token.networkId,
})
} else {
// if we add a non-specific amount of a given token
// sum up the value of all our UTXOs with this token
const relatedUtxoSum = utxos.reduce((value, next) => {
const assetEntry = next.nonDefaultEntries().find((entry) => entry.identifier === token.token.identifier)

if (assetEntry != null) {
return value.plus(assetEntry.amount)
}

return value
}, new BigNumber(0))
amount.add({
amount: relatedUtxoSum,
identifier: token.token.identifier,
networkId: token.token.networkId,
})
}
}

return amount
}
3 changes: 1 addition & 2 deletions src/legacy/ledgerUtils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,11 +18,10 @@ import {useMutation, UseMutationOptions} from 'react-query'
import {ledgerMessages} from '../i18n/global-messages'
import LocalizableError from '../i18n/LocalizableError'
import {Logger} from '../legacy/logging'
import {CardanoMobile, CardanoTypes} from '../yoroi-wallets'
import {CardanoMobile, CardanoTypes, normalizeToAddress, verifyFromBip44Root} from '../yoroi-wallets'
import type {Addressing, NetworkId, WalletImplementationId} from '../yoroi-wallets/types/other'
import {CONFIG, isByron, isHaskellShelley} from './config'
import {getNetworkConfigById} from './networks'
import {normalizeToAddress, verifyFromBip44Root} from './utils'

//
// ============== Errors ==================
Expand Down
183 changes: 0 additions & 183 deletions src/legacy/utils.ts
Original file line number Diff line number Diff line change
@@ -1,188 +1,5 @@
/* eslint-disable no-empty */

import {BigNumber} from 'bignumber.js'
import {isEmpty} from 'lodash'

import {asciiToHex, CardanoMobile, CardanoTypes, MultiToken, toAssetName, toPolicyId} from '../yoroi-wallets'
import type {Addressing, BaseAsset, NetworkId, RawUtxo} from '../yoroi-wallets/types/other'
import {CONFIG} from './config'
import {getNetworkConfigById} from './networks'

const PRIMARY_ASSET_CONSTANTS = CONFIG.PRIMARY_ASSET_CONSTANTS

export const normalizeToAddress = async (addr: string) => {
// in Shelley, addresses can be base16, bech32 or base58
// in this function, we try parsing in all encodings possible
// 1) Try converting from base58
try {
if (await CardanoMobile.ByronAddress.isValid(addr)) {
return await (await CardanoMobile.ByronAddress.fromBase58(addr)).toAddress()
}
} catch (_e) {}

// eslint-disable-line no-empty
// 2) If already base16, simply return
try {
return await CardanoMobile.Address.fromBytes(Buffer.from(addr, 'hex'))
} catch (_e) {}

// eslint-disable-line no-empty
// 3) Try converting from bech32
try {
return await CardanoMobile.Address.fromBech32(addr)
} catch (_e) {}

// eslint-disable-line no-empty
return undefined
}

// need to format shelley addresses as base16 but only legacy addresses as base58

export const verifyFromBip44Root = (request: Addressing['addressing']) => {
const accountPosition = request.startLevel

if (accountPosition !== CONFIG.NUMBERS.BIP44_DERIVATION_LEVELS.PURPOSE) {
throw new Error('verifyFromBip44Root: addressing does not start from root')
}

const lastLevelSpecified = request.startLevel + request.path.length - 1

if (lastLevelSpecified !== CONFIG.NUMBERS.BIP44_DERIVATION_LEVELS.ADDRESS) {
throw new Error('verifyFromBip44Root: incorrect addressing size')
}
}

export const deriveRewardAddressHex = async (accountPubKeyHex: string, networkId: NetworkId): Promise<string> => {
const accountPubKeyPtr = await CardanoMobile.Bip32PublicKey.fromBytes(Buffer.from(accountPubKeyHex, 'hex'))
const stakingKey = await (
await (
await accountPubKeyPtr.derive(CONFIG.NUMBERS.CHAIN_DERIVATIONS.CHIMERIC_ACCOUNT)
).derive(CONFIG.NUMBERS.STAKING_KEY_INDEX)
).toRawKey()
const credential = await CardanoMobile.StakeCredential.fromKeyhash(await stakingKey.hash())
let chainNetworkId = CONFIG.NETWORKS.HASKELL_SHELLEY.CHAIN_NETWORK_ID
// eslint-disable-next-line @typescript-eslint/no-explicit-any
const config: any = getNetworkConfigById(networkId)

if (config.CHAIN_NETWORK_ID != null) {
chainNetworkId = config.CHAIN_NETWORK_ID
}

const rewardAddr = await CardanoMobile.RewardAddress.new(parseInt(chainNetworkId, 10), credential)
const rewardAddrAsAddr = await rewardAddr.toAddress()
// eslint-disable-next-line @typescript-eslint/no-explicit-any
return Buffer.from((await rewardAddrAsAddr.toBytes()) as any, 'hex').toString('hex')
}

/**
* Multi-asset related
*/
export const identifierToCardanoAsset = async (
tokenId: string,
): Promise<{
policyId: CardanoTypes.ScriptHash
name: CardanoTypes.AssetName
}> => {
const policyId = toPolicyId(tokenId)
const assetNameHex = asciiToHex(toAssetName(tokenId) ?? '')

return {
policyId: await CardanoMobile.ScriptHash.fromBytes(Buffer.from(policyId, 'hex')),
name: await CardanoMobile.AssetName.new(Buffer.from(assetNameHex, 'hex')),
}
}

export const cardanoValueFromMultiToken = async (tokens: MultiToken) => {
const value = await CardanoMobile.Value.new(
await CardanoMobile.BigNum.fromStr(tokens.getDefaultEntry().amount.toString()),
)
// recall: primary asset counts towards size
if (tokens.size() === 1) return value
const assets = await CardanoMobile.MultiAsset.new()

for (const entry of tokens.nonDefaultEntries()) {
const {policyId, name} = await identifierToCardanoAsset(entry.identifier)
const asset = await assets.get(policyId)
const policyContent = asset.hasValue() ? asset : await CardanoMobile.Assets.new()

await policyContent.insert(name, await CardanoMobile.BigNum.fromStr(entry.amount.toString()))
// recall: we always have to insert since WASM returns copies of objects
await assets.insert(policyId, policyContent)
}

if ((await assets.len()) > 0) {
await value.setMultiasset(assets)
}

return value
}

export const cardanoValueFromRemoteFormat = async (utxo: RawUtxo) => {
const value = await CardanoMobile.Value.new(await CardanoMobile.BigNum.fromStr(utxo.amount))
if (utxo.assets.length === 0) return value
const assets = await CardanoMobile.MultiAsset.new()

for (const remoteAsset of utxo.assets) {
const {policyId, name} = await identifierToCardanoAsset(remoteAsset.assetId)
let policyContent = await assets.get(policyId)
policyContent = policyContent.hasValue() ? policyContent : await CardanoMobile.Assets.new()
await policyContent.insert(name, await CardanoMobile.BigNum.fromStr(remoteAsset.amount))
// recall: we always have to insert since WASM returns copies of objects
await assets.insert(policyId, policyContent)
}

if ((await assets.len()) > 0) {
await value.setMultiasset(assets)
}

return value
}
// matches RawUtxo and a tx input/output
type RemoteValue = {
readonly amount: string
readonly assets?: ReadonlyArray<BaseAsset>
}

export const multiTokenFromRemote = (remoteValue: RemoteValue, networkId: number) => {
const result = new MultiToken([], {
defaultNetworkId: networkId,
defaultIdentifier: PRIMARY_ASSET_CONSTANTS.CARDANO,
})
result.add({
identifier: PRIMARY_ASSET_CONSTANTS.CARDANO,
amount: new BigNumber(remoteValue.amount),
networkId,
})

if (remoteValue.assets != null) {
for (const token of remoteValue.assets) {
result.add({
identifier: token.assetId,
amount: new BigNumber(token.amount),
networkId,
})
}
}

return result
}

/**
* Wrapper function to lodash.isEmpty that
* returns true if the string is empty.
* The lodash.isEmpty function doesn't have the typescript's safeguard signature.
* It will be fixed in this PR https://github.com/DefinitelyTyped/DefinitelyTyped/pull/60401
*
* @summary Returns true if the value is empty: length === 0, null or undefined, else false.
*
* @param value The string to inspect
* @return {boolean} Returns true if the string is empty, else false.
*
* @example isEmptyString('') returns true
* @example isEmptyString(' ') returns false
* @example isEmptyString(null) returns true
* @example isEmptyString(undefined) returns true
*/
export function isEmptyString(value: string | null | undefined): value is '' | null | undefined {
return isEmpty(value)
}
6 changes: 3 additions & 3 deletions src/yoroi-wallets/cardano/CardanoWallet.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,10 +30,9 @@ import {
isHaskellShelleyNetwork,
isJormungandr,
} from '../../legacy/networks'
import {processTxHistoryData} from '../../legacy/processTransactions'
import {IsLockedError, nonblockingSynchronize, synchronize} from '../../legacy/promise'
import type {WalletMeta} from '../../legacy/state'
import {deriveRewardAddressHex} from '../../legacy/utils'
import {makeMemosManager, MemosManager} from '../memosManager'
import {YoroiStorage} from '../storage'
import type {
AccountStateResponse,
Expand Down Expand Up @@ -67,12 +66,13 @@ import {
} from '.'
import * as api from './api'
import {AddressChain, AddressChainJSON, Addresses, AddressGenerator} from './chain'
import {makeMemosManager, MemosManager} from './memosManager'
import {processTxHistoryData} from './processTransactions'
import {filterAddressesByStakingKey, getDelegationStatus} from './shelley/delegationUtils'
import {yoroiSignedTx} from './signedTx'
import {TransactionManager} from './transactionManager'
import {isYoroiWallet, NetworkId, WalletEvent, WalletImplementationId, WalletSubscription, YoroiWallet} from './types'
import {yoroiUnsignedTx} from './unsignedTx'
import {deriveRewardAddressHex} from './utils'
import {makeUtxoManager, UtxoManager} from './utxoManager'

type WalletState = {
Expand Down
2 changes: 1 addition & 1 deletion src/yoroi-wallets/cardano/assetUtils.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import BigNumber from 'bignumber.js'

import {getCardanoNetworkConfigById} from '../../legacy/networks'
import {cardanoValueFromRemoteFormat} from '../../legacy/utils'
import {NetworkId, RawUtxo} from '../types/other'
import {CardanoMobile} from '.'
import {cardanoValueFromRemoteFormat} from './utils'

export async function calcLockedDeposit(utxos: RawUtxo[], networkId: NetworkId) {
const networkConfig = getCardanoNetworkConfigById(networkId)
Expand Down

0 comments on commit 4225e89

Please sign in to comment.