@shapeshiftoss/utils 1.0.3 → 1.0.5
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/dist/cjs/.tsbuildinfo +1 -0
- package/dist/cjs/assertUnreachable.d.ts +1 -0
- package/dist/cjs/assertUnreachable.js +7 -0
- package/dist/cjs/assetData/assetData.test.d.ts +1 -0
- package/dist/cjs/assetData/assetData.test.js +136 -0
- package/dist/cjs/assetData/baseAssets.d.ts +30 -0
- package/dist/cjs/assetData/baseAssets.js +458 -0
- package/dist/cjs/assetData/constants.d.ts +1 -0
- package/dist/cjs/assetData/constants.js +13 -0
- package/dist/cjs/assetData/decodeAssetData.d.ts +7 -0
- package/dist/cjs/assetData/decodeAssetData.js +106 -0
- package/dist/cjs/assetData/decodeRelatedAssetIndex.d.ts +3 -0
- package/dist/cjs/assetData/decodeRelatedAssetIndex.js +14 -0
- package/dist/cjs/assetData/encodeAssetData.d.ts +4 -0
- package/dist/cjs/assetData/encodeAssetData.js +72 -0
- package/dist/cjs/assetData/encodeRelatedAssetIndex.d.ts +3 -0
- package/dist/cjs/assetData/encodeRelatedAssetIndex.js +20 -0
- package/dist/cjs/assetData/getBaseAsset.d.ts +3 -0
- package/dist/cjs/assetData/getBaseAsset.js +66 -0
- package/dist/cjs/assetData/index.d.ts +7 -0
- package/dist/cjs/assetData/index.js +23 -0
- package/dist/cjs/assetData/relatedAssetIndex.test.d.ts +1 -0
- package/dist/cjs/assetData/relatedAssetIndex.test.js +32 -0
- package/dist/cjs/assetData/types.d.ts +28 -0
- package/dist/cjs/assetData/types.js +2 -0
- package/dist/cjs/baseUnits/baseUnits.d.ts +5 -0
- package/dist/cjs/baseUnits/baseUnits.js +32 -0
- package/dist/cjs/baseUnits/baseUnits.test.d.ts +1 -0
- package/dist/cjs/baseUnits/baseUnits.test.js +32 -0
- package/dist/cjs/basisPoints.d.ts +23 -0
- package/dist/cjs/basisPoints.js +48 -0
- package/dist/cjs/bignumber/bignumber.d.ts +11 -0
- package/dist/cjs/bignumber/bignumber.js +27 -0
- package/dist/cjs/bignumber/bignumber.test.d.ts +1 -0
- package/dist/cjs/bignumber/bignumber.test.js +52 -0
- package/dist/cjs/chainIdToFeeAsset.d.ts +3 -0
- package/dist/cjs/chainIdToFeeAsset.js +9 -0
- package/dist/cjs/chainIdToFeeAssetId.d.ts +2 -0
- package/dist/cjs/chainIdToFeeAssetId.js +66 -0
- package/dist/cjs/createThrottle.d.ts +9 -0
- package/dist/cjs/createThrottle.js +36 -0
- package/dist/cjs/getAssetNamespaceFromChainId.d.ts +3 -0
- package/dist/cjs/getAssetNamespaceFromChainId.js +46 -0
- package/dist/cjs/getChainShortName.d.ts +2 -0
- package/dist/cjs/getChainShortName.js +65 -0
- package/dist/cjs/getNativeFeeAssetReference.d.ts +2 -0
- package/dist/cjs/getNativeFeeAssetReference.js +105 -0
- package/dist/cjs/historyTimeframe.d.ts +6 -0
- package/dist/cjs/historyTimeframe.js +36 -0
- package/dist/cjs/index.d.ts +24 -0
- package/dist/cjs/index.js +62 -0
- package/dist/cjs/makeAsset/makeAsset.d.ts +10 -0
- package/dist/cjs/makeAsset/makeAsset.js +45 -0
- package/dist/cjs/makeAsset/makeAsset.test.d.ts +1 -0
- package/dist/cjs/makeAsset/makeAsset.test.js +47 -0
- package/dist/cjs/package.json +1 -0
- package/dist/cjs/promises.d.ts +4 -0
- package/dist/cjs/promises.js +9 -0
- package/dist/cjs/sha256.d.ts +1 -0
- package/dist/cjs/sha256.js +9 -0
- package/dist/cjs/timeout.d.ts +7 -0
- package/dist/cjs/timeout.js +34 -0
- package/dist/cjs/treasury.d.ts +17 -0
- package/dist/cjs/treasury.js +36 -0
- package/dist/cjs/unfreeze.d.ts +4 -0
- package/dist/cjs/unfreeze.js +10 -0
- package/dist/cjs/utxo.d.ts +2 -0
- package/dist/cjs/utxo.js +6 -0
- package/dist/esm/.tsbuildinfo +1 -0
- package/dist/esm/assertUnreachable.d.ts +1 -0
- package/dist/esm/assertUnreachable.js +3 -0
- package/dist/esm/assetData/assetData.test.d.ts +1 -0
- package/dist/esm/assetData/assetData.test.js +134 -0
- package/dist/esm/assetData/baseAssets.d.ts +30 -0
- package/dist/esm/assetData/baseAssets.js +432 -0
- package/dist/esm/assetData/constants.d.ts +1 -0
- package/dist/esm/assetData/constants.js +10 -0
- package/dist/esm/assetData/decodeAssetData.d.ts +7 -0
- package/dist/esm/assetData/decodeAssetData.js +102 -0
- package/dist/esm/assetData/decodeRelatedAssetIndex.d.ts +3 -0
- package/dist/esm/assetData/decodeRelatedAssetIndex.js +10 -0
- package/dist/esm/assetData/encodeAssetData.d.ts +4 -0
- package/dist/esm/assetData/encodeAssetData.js +68 -0
- package/dist/esm/assetData/encodeRelatedAssetIndex.d.ts +3 -0
- package/dist/esm/assetData/encodeRelatedAssetIndex.js +16 -0
- package/dist/esm/assetData/getBaseAsset.d.ts +3 -0
- package/dist/esm/assetData/getBaseAsset.js +62 -0
- package/dist/esm/assetData/index.d.ts +7 -0
- package/dist/esm/assetData/index.js +7 -0
- package/dist/esm/assetData/relatedAssetIndex.test.d.ts +1 -0
- package/dist/esm/assetData/relatedAssetIndex.test.js +30 -0
- package/dist/esm/assetData/types.d.ts +28 -0
- package/dist/esm/assetData/types.js +1 -0
- package/dist/esm/baseUnits/baseUnits.d.ts +5 -0
- package/dist/esm/baseUnits/baseUnits.js +23 -0
- package/dist/esm/baseUnits/baseUnits.test.d.ts +1 -0
- package/dist/esm/baseUnits/baseUnits.test.js +30 -0
- package/dist/esm/basisPoints.d.ts +23 -0
- package/dist/esm/basisPoints.js +39 -0
- package/dist/esm/bignumber/bignumber.d.ts +11 -0
- package/dist/esm/bignumber/bignumber.js +16 -0
- package/dist/esm/bignumber/bignumber.test.d.ts +1 -0
- package/dist/esm/bignumber/bignumber.test.js +50 -0
- package/dist/esm/chainIdToFeeAsset.d.ts +3 -0
- package/dist/esm/chainIdToFeeAsset.js +5 -0
- package/dist/esm/chainIdToFeeAssetId.d.ts +2 -0
- package/dist/esm/chainIdToFeeAssetId.js +62 -0
- package/dist/esm/createThrottle.d.ts +9 -0
- package/dist/esm/createThrottle.js +32 -0
- package/dist/esm/getAssetNamespaceFromChainId.d.ts +3 -0
- package/dist/esm/getAssetNamespaceFromChainId.js +42 -0
- package/dist/esm/getChainShortName.d.ts +2 -0
- package/dist/esm/getChainShortName.js +61 -0
- package/dist/esm/getNativeFeeAssetReference.d.ts +2 -0
- package/dist/esm/getNativeFeeAssetReference.js +101 -0
- package/dist/esm/historyTimeframe.d.ts +6 -0
- package/dist/esm/historyTimeframe.js +29 -0
- package/dist/esm/index.d.ts +24 -0
- package/dist/esm/index.js +41 -0
- package/dist/esm/makeAsset/makeAsset.d.ts +10 -0
- package/dist/esm/makeAsset/makeAsset.js +41 -0
- package/dist/esm/makeAsset/makeAsset.test.d.ts +1 -0
- package/dist/esm/makeAsset/makeAsset.test.js +45 -0
- package/dist/esm/promises.d.ts +4 -0
- package/dist/esm/promises.js +3 -0
- package/dist/esm/sha256.d.ts +1 -0
- package/dist/esm/sha256.js +2 -0
- package/dist/esm/timeout.d.ts +7 -0
- package/dist/esm/timeout.js +28 -0
- package/dist/esm/treasury.d.ts +17 -0
- package/dist/esm/treasury.js +32 -0
- package/dist/esm/unfreeze.d.ts +4 -0
- package/dist/esm/unfreeze.js +6 -0
- package/dist/esm/utxo.d.ts +2 -0
- package/dist/esm/utxo.js +2 -0
- package/package.json +3 -3
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
import { fromAssetId } from '@shapeshiftoss/caip';
|
|
2
|
+
import { pick } from 'lodash';
|
|
3
|
+
import { assertUnreachable } from '../assertUnreachable.js';
|
|
4
|
+
import { FIELDS } from './constants.js';
|
|
5
|
+
import { getBaseAsset } from './getBaseAsset.js';
|
|
6
|
+
const decodeAssetId = (encodedAssetId, assetIdPrefixes) => {
|
|
7
|
+
// Performance sensitive. `lastIndexOf` + `substring` faster than `split`
|
|
8
|
+
const colonIndex = encodedAssetId.lastIndexOf(':');
|
|
9
|
+
const prefixIdx = Number(encodedAssetId.substring(0, colonIndex));
|
|
10
|
+
const assetReference = encodedAssetId.substring(colonIndex + 1);
|
|
11
|
+
// Performance sensitive. String concatenation faster than template literal
|
|
12
|
+
return assetIdPrefixes[prefixIdx] + ':' + assetReference;
|
|
13
|
+
};
|
|
14
|
+
export const decodeAssetData = (encodedAssetData, shouldAddNetworkName = false) => {
|
|
15
|
+
const { assetIdPrefixes, encodedAssetIds, encodedAssets } = encodedAssetData;
|
|
16
|
+
const sortedAssetIds = encodedAssetIds.map(encodedAssetId => decodeAssetId(encodedAssetId, assetIdPrefixes));
|
|
17
|
+
const assetData = encodedAssets.reduce((acc, encodedAsset, idx) => {
|
|
18
|
+
const assetId = sortedAssetIds[idx];
|
|
19
|
+
const { chainId } = fromAssetId(assetId);
|
|
20
|
+
const baseAsset = getBaseAsset(chainId);
|
|
21
|
+
// Initialize with default values for the chain
|
|
22
|
+
const asset = Object.assign({
|
|
23
|
+
assetId,
|
|
24
|
+
chainId,
|
|
25
|
+
symbol: '',
|
|
26
|
+
name: '',
|
|
27
|
+
precision: 0,
|
|
28
|
+
color: '',
|
|
29
|
+
icon: undefined,
|
|
30
|
+
explorer: '',
|
|
31
|
+
explorerAddressLink: '',
|
|
32
|
+
explorerTxLink: '',
|
|
33
|
+
relatedAssetKey: null,
|
|
34
|
+
}, pick(baseAsset, ['explorer', 'explorerAddressLink', 'explorerTxLink']));
|
|
35
|
+
if (assetId === baseAsset?.assetId) {
|
|
36
|
+
asset.networkName = baseAsset.networkName;
|
|
37
|
+
asset.networkIcon = baseAsset.networkIcon;
|
|
38
|
+
asset.networkColor = baseAsset.networkColor;
|
|
39
|
+
}
|
|
40
|
+
// Apply each field's decoded value to the asset
|
|
41
|
+
FIELDS.forEach((field, fieldIdx) => {
|
|
42
|
+
const value = encodedAsset[fieldIdx];
|
|
43
|
+
switch (field) {
|
|
44
|
+
case 'icon': {
|
|
45
|
+
const iconOrIcons = value;
|
|
46
|
+
if (iconOrIcons.length === 1) {
|
|
47
|
+
asset.icon = iconOrIcons[0];
|
|
48
|
+
}
|
|
49
|
+
else if (iconOrIcons.length > 1) {
|
|
50
|
+
asset.icons = iconOrIcons;
|
|
51
|
+
}
|
|
52
|
+
break;
|
|
53
|
+
}
|
|
54
|
+
case 'relatedAssetKey': {
|
|
55
|
+
const assetIdx = value;
|
|
56
|
+
const relatedAssetId = assetIdx === null ? null : sortedAssetIds[assetIdx];
|
|
57
|
+
// if (relatedAssetId === undefined) throw Error()
|
|
58
|
+
if (relatedAssetId &&
|
|
59
|
+
relatedAssetId !== asset.assetId &&
|
|
60
|
+
baseAsset.networkName &&
|
|
61
|
+
shouldAddNetworkName) {
|
|
62
|
+
asset.name = `${asset.name} on ${baseAsset.networkName}`;
|
|
63
|
+
}
|
|
64
|
+
asset.relatedAssetKey = relatedAssetId;
|
|
65
|
+
asset.isPrimary = relatedAssetId === null || relatedAssetId === asset.assetId;
|
|
66
|
+
asset.isChainSpecific = relatedAssetId === null;
|
|
67
|
+
break;
|
|
68
|
+
}
|
|
69
|
+
case 'name':
|
|
70
|
+
asset.name = value;
|
|
71
|
+
break;
|
|
72
|
+
case 'precision':
|
|
73
|
+
asset.precision = value;
|
|
74
|
+
break;
|
|
75
|
+
case 'color':
|
|
76
|
+
asset.color = value;
|
|
77
|
+
break;
|
|
78
|
+
case 'symbol':
|
|
79
|
+
asset.symbol = value;
|
|
80
|
+
break;
|
|
81
|
+
case 'isPool': {
|
|
82
|
+
const isPool = value;
|
|
83
|
+
if (isPool) {
|
|
84
|
+
asset.isPool = true;
|
|
85
|
+
}
|
|
86
|
+
break;
|
|
87
|
+
}
|
|
88
|
+
case 'assetIdx':
|
|
89
|
+
// Skip assetIdx as we already have assetId
|
|
90
|
+
break;
|
|
91
|
+
default:
|
|
92
|
+
assertUnreachable(field);
|
|
93
|
+
}
|
|
94
|
+
});
|
|
95
|
+
acc[assetId] = asset;
|
|
96
|
+
return acc;
|
|
97
|
+
}, {});
|
|
98
|
+
return {
|
|
99
|
+
assetData,
|
|
100
|
+
sortedAssetIds,
|
|
101
|
+
};
|
|
102
|
+
};
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
export const decodeRelatedAssetIndex = (encodedRelatedAssetIndex, sortedAssetIds) => {
|
|
2
|
+
const result = {};
|
|
3
|
+
for (let assetIdx = 0; assetIdx < sortedAssetIds.length; assetIdx++) {
|
|
4
|
+
const assetId = sortedAssetIds[assetIdx];
|
|
5
|
+
if (!encodedRelatedAssetIndex[assetIdx])
|
|
6
|
+
continue;
|
|
7
|
+
result[assetId] = encodedRelatedAssetIndex[assetIdx].map(innerAssetIdx => sortedAssetIds[innerAssetIdx]);
|
|
8
|
+
}
|
|
9
|
+
return result;
|
|
10
|
+
};
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { AssetId } from '@shapeshiftoss/caip';
|
|
2
|
+
import type { AssetsById } from '@shapeshiftoss/types';
|
|
3
|
+
import type { EncodedAssetData } from './types.js';
|
|
4
|
+
export declare const encodeAssetData: (sortedAssetIds: AssetId[], assetsById: AssetsById) => EncodedAssetData;
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import { assertUnreachable } from '../assertUnreachable.js';
|
|
2
|
+
import { FIELDS } from './constants.js';
|
|
3
|
+
const encodeAssetIds = (sortedAssetIds) => {
|
|
4
|
+
const assetIdPrefixes = [];
|
|
5
|
+
const encodedAssetIds = [];
|
|
6
|
+
for (const assetId of sortedAssetIds) {
|
|
7
|
+
// `indexOf` + `substring` faster than `split`
|
|
8
|
+
const colonIndex = assetId.lastIndexOf(':');
|
|
9
|
+
const prefix = assetId.substring(0, colonIndex);
|
|
10
|
+
const assetReference = assetId.substring(colonIndex + 1);
|
|
11
|
+
const prefixIdx = (() => {
|
|
12
|
+
const prefixIdx = assetIdPrefixes.indexOf(prefix);
|
|
13
|
+
if (prefixIdx !== -1) {
|
|
14
|
+
return prefixIdx;
|
|
15
|
+
}
|
|
16
|
+
else {
|
|
17
|
+
assetIdPrefixes.push(prefix);
|
|
18
|
+
return assetIdPrefixes.length - 1;
|
|
19
|
+
}
|
|
20
|
+
})();
|
|
21
|
+
encodedAssetIds.push(`${prefixIdx}:${assetReference}`);
|
|
22
|
+
}
|
|
23
|
+
return {
|
|
24
|
+
assetIdPrefixes,
|
|
25
|
+
encodedAssetIds,
|
|
26
|
+
};
|
|
27
|
+
};
|
|
28
|
+
const encodeField = (field, assetIdToAssetIdx, asset) => {
|
|
29
|
+
switch (field) {
|
|
30
|
+
case 'assetIdx':
|
|
31
|
+
return assetIdToAssetIdx[asset.assetId];
|
|
32
|
+
case 'name':
|
|
33
|
+
return asset.name;
|
|
34
|
+
case 'precision':
|
|
35
|
+
return asset.precision;
|
|
36
|
+
case 'color':
|
|
37
|
+
return asset.color;
|
|
38
|
+
case 'icon':
|
|
39
|
+
return (asset.icon ? [asset.icon] : asset.icons ?? []);
|
|
40
|
+
case 'symbol':
|
|
41
|
+
return asset.symbol;
|
|
42
|
+
case 'relatedAssetKey':
|
|
43
|
+
return (!asset.relatedAssetKey ? null : assetIdToAssetIdx[asset.relatedAssetKey]);
|
|
44
|
+
case 'isPool':
|
|
45
|
+
return (asset.isPool ? 1 : 0);
|
|
46
|
+
default:
|
|
47
|
+
return assertUnreachable(field);
|
|
48
|
+
}
|
|
49
|
+
};
|
|
50
|
+
export const encodeAssetData = (sortedAssetIds, assetsById) => {
|
|
51
|
+
const { assetIdPrefixes, encodedAssetIds } = encodeAssetIds(sortedAssetIds);
|
|
52
|
+
const assetIdToAssetIdx = sortedAssetIds.reduce((acc, val, idx) => {
|
|
53
|
+
acc[val] = idx;
|
|
54
|
+
return acc;
|
|
55
|
+
}, {});
|
|
56
|
+
const encodedAssets = [];
|
|
57
|
+
for (let i = 0; i < encodedAssetIds.length; i++) {
|
|
58
|
+
const assetId = sortedAssetIds[i];
|
|
59
|
+
const asset = assetsById[assetId];
|
|
60
|
+
const record = FIELDS.map(field => encodeField(field, assetIdToAssetIdx, asset));
|
|
61
|
+
encodedAssets.push(record);
|
|
62
|
+
}
|
|
63
|
+
return {
|
|
64
|
+
assetIdPrefixes,
|
|
65
|
+
encodedAssetIds,
|
|
66
|
+
encodedAssets,
|
|
67
|
+
};
|
|
68
|
+
};
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
export const encodeRelatedAssetIndex = (relatedAssetIndex, sortedAssetIds) => {
|
|
2
|
+
const assetIdToAssetIdx = sortedAssetIds.reduce((acc, val, idx) => {
|
|
3
|
+
acc[val] = idx;
|
|
4
|
+
return acc;
|
|
5
|
+
}, {});
|
|
6
|
+
const result = {};
|
|
7
|
+
for (const [assetId, relatedAssets] of Object.entries(relatedAssetIndex)) {
|
|
8
|
+
if (!relatedAssets.length)
|
|
9
|
+
continue;
|
|
10
|
+
const assetIdx = assetIdToAssetIdx[assetId];
|
|
11
|
+
result[assetIdx] = relatedAssets.map(assetId => {
|
|
12
|
+
return assetIdToAssetIdx[assetId];
|
|
13
|
+
});
|
|
14
|
+
}
|
|
15
|
+
return result;
|
|
16
|
+
};
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
import { KnownChainIds } from '@shapeshiftoss/types';
|
|
2
|
+
import { assertUnreachable } from '../assertUnreachable.js';
|
|
3
|
+
import { arbitrum, arbitrumNova, atom, avax, base, bitcoin, bitcoincash, bnbsmartchain, dogecoin, ethereum, gnosis, hyperevm, katana, litecoin, mayachain, monad, near, optimism, plasma, polygon, solana, starknet, sui, thorchain, tron, zcash, } from './baseAssets.js';
|
|
4
|
+
export const getBaseAsset = (chainId) => {
|
|
5
|
+
const knownChainId = chainId;
|
|
6
|
+
switch (knownChainId) {
|
|
7
|
+
case KnownChainIds.EthereumMainnet:
|
|
8
|
+
return ethereum;
|
|
9
|
+
case KnownChainIds.AvalancheMainnet:
|
|
10
|
+
return avax;
|
|
11
|
+
case KnownChainIds.OptimismMainnet:
|
|
12
|
+
return optimism;
|
|
13
|
+
case KnownChainIds.BnbSmartChainMainnet:
|
|
14
|
+
return bnbsmartchain;
|
|
15
|
+
case KnownChainIds.PolygonMainnet:
|
|
16
|
+
return polygon;
|
|
17
|
+
case KnownChainIds.GnosisMainnet:
|
|
18
|
+
return gnosis;
|
|
19
|
+
case KnownChainIds.ArbitrumMainnet:
|
|
20
|
+
return arbitrum;
|
|
21
|
+
case KnownChainIds.ArbitrumNovaMainnet:
|
|
22
|
+
return arbitrumNova;
|
|
23
|
+
case KnownChainIds.BaseMainnet:
|
|
24
|
+
return base;
|
|
25
|
+
case KnownChainIds.SolanaMainnet:
|
|
26
|
+
return solana;
|
|
27
|
+
case KnownChainIds.SuiMainnet:
|
|
28
|
+
return sui;
|
|
29
|
+
case KnownChainIds.StarknetMainnet:
|
|
30
|
+
return starknet;
|
|
31
|
+
case KnownChainIds.BitcoinMainnet:
|
|
32
|
+
return bitcoin;
|
|
33
|
+
case KnownChainIds.BitcoinCashMainnet:
|
|
34
|
+
return bitcoincash;
|
|
35
|
+
case KnownChainIds.DogecoinMainnet:
|
|
36
|
+
return dogecoin;
|
|
37
|
+
case KnownChainIds.LitecoinMainnet:
|
|
38
|
+
return litecoin;
|
|
39
|
+
case KnownChainIds.CosmosMainnet:
|
|
40
|
+
return atom;
|
|
41
|
+
case KnownChainIds.ThorchainMainnet:
|
|
42
|
+
return thorchain;
|
|
43
|
+
case KnownChainIds.MayachainMainnet:
|
|
44
|
+
return mayachain;
|
|
45
|
+
case KnownChainIds.TronMainnet:
|
|
46
|
+
return tron;
|
|
47
|
+
case KnownChainIds.MonadMainnet:
|
|
48
|
+
return monad;
|
|
49
|
+
case KnownChainIds.HyperEvmMainnet:
|
|
50
|
+
return hyperevm;
|
|
51
|
+
case KnownChainIds.PlasmaMainnet:
|
|
52
|
+
return plasma;
|
|
53
|
+
case KnownChainIds.KatanaMainnet:
|
|
54
|
+
return katana;
|
|
55
|
+
case KnownChainIds.NearMainnet:
|
|
56
|
+
return near;
|
|
57
|
+
case KnownChainIds.ZcashMainnet:
|
|
58
|
+
return zcash;
|
|
59
|
+
default:
|
|
60
|
+
return assertUnreachable(knownChainId);
|
|
61
|
+
}
|
|
62
|
+
};
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
export * from './encodeAssetData.js';
|
|
2
|
+
export * from './decodeAssetData.js';
|
|
3
|
+
export * from './baseAssets.js';
|
|
4
|
+
export * from './getBaseAsset.js';
|
|
5
|
+
export * from './encodeRelatedAssetIndex.js';
|
|
6
|
+
export * from './decodeRelatedAssetIndex.js';
|
|
7
|
+
export * from './types.js';
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
export * from './encodeAssetData.js';
|
|
2
|
+
export * from './decodeAssetData.js';
|
|
3
|
+
export * from './baseAssets.js';
|
|
4
|
+
export * from './getBaseAsset.js';
|
|
5
|
+
export * from './encodeRelatedAssetIndex.js';
|
|
6
|
+
export * from './decodeRelatedAssetIndex.js';
|
|
7
|
+
export * from './types.js';
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { describe, expect, it } from 'vitest';
|
|
2
|
+
import { decodeRelatedAssetIndex } from './decodeRelatedAssetIndex.js';
|
|
3
|
+
import { encodeRelatedAssetIndex } from './encodeRelatedAssetIndex.js';
|
|
4
|
+
// Order of these is deliberately shuffled to test sorting is preserved
|
|
5
|
+
const mockSortedAssetIds = [
|
|
6
|
+
'eip155:1/erc20:0xeeecd285f60e802ecb6d8d8d37790c887f9a4b33',
|
|
7
|
+
'eip155:1/erc20:0xeeee2a2e650697d2a8e8bc990c2f3d04203be06f',
|
|
8
|
+
'eip155:1/erc20:0xeed3ae7b0f8b5b9bb8c035a9941382b1822671cd',
|
|
9
|
+
'eip155:1/erc20:0xf073bac22dab7faf4a3dd6c6189a70d54110525c',
|
|
10
|
+
'eip155:1/erc20:0xeee0fe52299f2de8e2ed5111cd521ab67dcf0faf',
|
|
11
|
+
'eip155:1/erc20:0xeeda34a377dd0ca676b9511ee1324974fa8d980d',
|
|
12
|
+
'bip122:000000000019d6689c085ae165831e93/slip44:0', // BTC
|
|
13
|
+
];
|
|
14
|
+
const mockRelatedAssetIndex = {
|
|
15
|
+
'eip155:1/erc20:0xeeee2a2e650697d2a8e8bc990c2f3d04203be06f': [
|
|
16
|
+
'eip155:1/erc20:0xeeee2a2e650697d2a8e8bc990c2f3d04203be06f',
|
|
17
|
+
'eip155:1/erc20:0xf073bac22dab7faf4a3dd6c6189a70d54110525c',
|
|
18
|
+
],
|
|
19
|
+
'eip155:1/erc20:0xf073bac22dab7faf4a3dd6c6189a70d54110525c': [
|
|
20
|
+
'eip155:1/erc20:0xeeee2a2e650697d2a8e8bc990c2f3d04203be06f',
|
|
21
|
+
'eip155:1/erc20:0xf073bac22dab7faf4a3dd6c6189a70d54110525c',
|
|
22
|
+
],
|
|
23
|
+
};
|
|
24
|
+
describe('relatedAssetIndex', () => {
|
|
25
|
+
it('can encode and decode related asset index as a complete round trip', () => {
|
|
26
|
+
const encodedRelatedAssetIndex = encodeRelatedAssetIndex(mockRelatedAssetIndex, mockSortedAssetIds);
|
|
27
|
+
const decodedRelatedAssetIndex = decodeRelatedAssetIndex(encodedRelatedAssetIndex, mockSortedAssetIds);
|
|
28
|
+
expect(decodedRelatedAssetIndex).toEqual(mockRelatedAssetIndex);
|
|
29
|
+
});
|
|
30
|
+
});
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import type { FIELDS } from './constants.js';
|
|
2
|
+
export type Field = (typeof FIELDS)[number];
|
|
3
|
+
export type FieldToType = {
|
|
4
|
+
assetIdx: number;
|
|
5
|
+
name: string;
|
|
6
|
+
precision: number;
|
|
7
|
+
color: string;
|
|
8
|
+
icon: string[];
|
|
9
|
+
symbol: string;
|
|
10
|
+
relatedAssetKey: number | null;
|
|
11
|
+
isPool: 0 | 1;
|
|
12
|
+
};
|
|
13
|
+
export type EncodedAsset = [
|
|
14
|
+
FieldToType['assetIdx'],
|
|
15
|
+
FieldToType['name'],
|
|
16
|
+
FieldToType['precision'],
|
|
17
|
+
FieldToType['color'],
|
|
18
|
+
FieldToType['icon'],
|
|
19
|
+
FieldToType['symbol'],
|
|
20
|
+
FieldToType['relatedAssetKey'],
|
|
21
|
+
FieldToType['isPool']
|
|
22
|
+
];
|
|
23
|
+
export type EncodedAssetData = {
|
|
24
|
+
assetIdPrefixes: string[];
|
|
25
|
+
encodedAssetIds: string[];
|
|
26
|
+
encodedAssets: EncodedAsset[];
|
|
27
|
+
};
|
|
28
|
+
export type EncodedRelatedAssetIndex = Record<number, number[]>;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import BigNumber from 'bignumber.js';
|
|
2
|
+
import type { BN } from '../bignumber/bignumber.js';
|
|
3
|
+
export declare const fromBaseUnit: (value: BigNumber.Value, precision: number, displayDecimals?: number) => string;
|
|
4
|
+
export declare const toBaseUnit: (amount: BigNumber.Value | undefined, precision: number, roundingMode?: BigNumber.RoundingMode) => string;
|
|
5
|
+
export declare const firstNonZeroDecimal: (number: BN) => string | undefined;
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import BigNumber from 'bignumber.js';
|
|
2
|
+
import { bn, bnOrZero } from '../bignumber/bignumber.js';
|
|
3
|
+
// Converts from base unit to a precision/ish number
|
|
4
|
+
// - If no displayDecimals are provided, it will use the full precision of the number being converted
|
|
5
|
+
// - If displayDecimals are provided, it will use that precision, to return e.g a human, precision, or number stripped to any arbitrary decimal places
|
|
6
|
+
// and use the ROUND_DOWN rounding mode
|
|
7
|
+
export const fromBaseUnit = (value, precision, displayDecimals) => {
|
|
8
|
+
const precisionNumber = bnOrZero(value).div(bn(10).pow(precision));
|
|
9
|
+
if (typeof displayDecimals === 'number') {
|
|
10
|
+
return precisionNumber
|
|
11
|
+
.decimalPlaces(displayDecimals, BigNumber.ROUND_DOWN)
|
|
12
|
+
.toFixed(displayDecimals);
|
|
13
|
+
}
|
|
14
|
+
return precisionNumber.toFixed();
|
|
15
|
+
};
|
|
16
|
+
export const toBaseUnit = (amount, precision, roundingMode) => {
|
|
17
|
+
return bnOrZero(amount)
|
|
18
|
+
.times(bn(10).exponentiatedBy(bnOrZero(precision)))
|
|
19
|
+
.toFixed(0, roundingMode);
|
|
20
|
+
};
|
|
21
|
+
export const firstNonZeroDecimal = (number) => {
|
|
22
|
+
return number.toFixed(10).match(/^-?\d*\.?0*\d{0,2}/)?.[0];
|
|
23
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { describe, expect, it } from 'vitest';
|
|
2
|
+
import { fromBaseUnit } from './baseUnits.js';
|
|
3
|
+
describe('@/lib/math', () => {
|
|
4
|
+
describe('fromBaseUnit', () => {
|
|
5
|
+
it('should correctly convert and round down with given displayDecimals', () => {
|
|
6
|
+
const result = fromBaseUnit(123456789, 4, 2);
|
|
7
|
+
expect(result).toBe('12345.67');
|
|
8
|
+
});
|
|
9
|
+
it('should correctly convert without displayDecimals and return full precision', () => {
|
|
10
|
+
const result = fromBaseUnit(123456789, 4);
|
|
11
|
+
expect(result).toBe('12345.6789');
|
|
12
|
+
});
|
|
13
|
+
it('should correctly convert and round down with given displayDecimals for another input', () => {
|
|
14
|
+
const result = fromBaseUnit(987654321, 6, 3);
|
|
15
|
+
expect(result).toBe('987.654');
|
|
16
|
+
});
|
|
17
|
+
it('should correctly convert without displayDecimals and return full precision for another input', () => {
|
|
18
|
+
const result = fromBaseUnit(987654321, 6);
|
|
19
|
+
expect(result).toBe('987.654321');
|
|
20
|
+
});
|
|
21
|
+
it('should correctly convert and round down with given displayDecimals for high precision input', () => {
|
|
22
|
+
const result = fromBaseUnit('182912819182912192', 18, 8);
|
|
23
|
+
expect(result).toBe('0.18291281');
|
|
24
|
+
});
|
|
25
|
+
it('should correctly convert without displayDecimals and return full precision for high precision input', () => {
|
|
26
|
+
const result = fromBaseUnit('182912819182912192', 18);
|
|
27
|
+
expect(result).toBe('0.182912819182912192');
|
|
28
|
+
});
|
|
29
|
+
});
|
|
30
|
+
});
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import type { BigNumber } from './bignumber/bignumber.js';
|
|
2
|
+
export declare const convertBasisPointsToDecimalPercentage: (basisPoints: BigNumber.Value) => BigNumber;
|
|
3
|
+
export declare const convertDecimalPercentageToBasisPoints: (decimalPercentage: BigNumber.Value) => BigNumber;
|
|
4
|
+
export declare const convertBasisPointsToPercentage: (basisPoints: BigNumber.Value) => BigNumber;
|
|
5
|
+
export declare const convertPercentageToBasisPoints: (percentage: BigNumber.Value) => BigNumber;
|
|
6
|
+
/**
|
|
7
|
+
* Subtracts basis point amount from a given value.
|
|
8
|
+
*
|
|
9
|
+
* @param value The value to subtract basis points from.
|
|
10
|
+
* @param basisPoints The number of basis points to subtract.
|
|
11
|
+
* @param roundingMode
|
|
12
|
+
* @returns The new number that is the input value minus the basis points of the value.
|
|
13
|
+
*/
|
|
14
|
+
export declare const subtractBasisPointAmount: (value: string, basisPoints: BigNumber.Value, roundingMode?: BigNumber.RoundingMode) => string;
|
|
15
|
+
/**
|
|
16
|
+
* Adds basis point amount from a given value.
|
|
17
|
+
*
|
|
18
|
+
* @param value The value to subtract basis points from.
|
|
19
|
+
* @param basisPoints The number of basis points to subtract.
|
|
20
|
+
* @param roundingMode
|
|
21
|
+
* @returns The new number that is the input value minus the basis points of the value.
|
|
22
|
+
*/
|
|
23
|
+
export declare const addBasisPointAmount: (value: string, basisPoints: BigNumber.Value, roundingMode?: BigNumber.RoundingMode) => string;
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import { bn, bnOrZero } from './bignumber/bignumber.js';
|
|
2
|
+
export const convertBasisPointsToDecimalPercentage = (basisPoints) => bnOrZero(basisPoints).div(10000);
|
|
3
|
+
export const convertDecimalPercentageToBasisPoints = (decimalPercentage) => bnOrZero(decimalPercentage).times(10000);
|
|
4
|
+
export const convertBasisPointsToPercentage = (basisPoints) => bnOrZero(basisPoints).div(100);
|
|
5
|
+
export const convertPercentageToBasisPoints = (percentage) => bnOrZero(percentage).times(100);
|
|
6
|
+
/**
|
|
7
|
+
* Subtracts basis point amount from a given value.
|
|
8
|
+
*
|
|
9
|
+
* @param value The value to subtract basis points from.
|
|
10
|
+
* @param basisPoints The number of basis points to subtract.
|
|
11
|
+
* @param roundingMode
|
|
12
|
+
* @returns The new number that is the input value minus the basis points of the value.
|
|
13
|
+
*/
|
|
14
|
+
export const subtractBasisPointAmount = (value, basisPoints, roundingMode) => {
|
|
15
|
+
const bigNumValue = bn(value);
|
|
16
|
+
// Basis point is 1/100th of a percent
|
|
17
|
+
const percentValue = convertBasisPointsToDecimalPercentage(basisPoints);
|
|
18
|
+
const subtractValue = bigNumValue.times(percentValue);
|
|
19
|
+
// Subtract basis points from the original value
|
|
20
|
+
const resultValue = bigNumValue.minus(subtractValue);
|
|
21
|
+
return roundingMode !== undefined ? resultValue.toFixed(0, roundingMode) : resultValue.toFixed();
|
|
22
|
+
};
|
|
23
|
+
/**
|
|
24
|
+
* Adds basis point amount from a given value.
|
|
25
|
+
*
|
|
26
|
+
* @param value The value to subtract basis points from.
|
|
27
|
+
* @param basisPoints The number of basis points to subtract.
|
|
28
|
+
* @param roundingMode
|
|
29
|
+
* @returns The new number that is the input value minus the basis points of the value.
|
|
30
|
+
*/
|
|
31
|
+
export const addBasisPointAmount = (value, basisPoints, roundingMode) => {
|
|
32
|
+
const bigNumValue = bn(value);
|
|
33
|
+
// Basis point is 1/100th of a percent
|
|
34
|
+
const percentValue = convertBasisPointsToDecimalPercentage(basisPoints);
|
|
35
|
+
const addValue = bigNumValue.times(percentValue);
|
|
36
|
+
// Subtract basis points from the original value
|
|
37
|
+
const resultValue = bigNumValue.plus(addValue);
|
|
38
|
+
return roundingMode !== undefined ? resultValue.toFixed(0, roundingMode) : resultValue.toFixed();
|
|
39
|
+
};
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import BigNumber from 'bignumber.js';
|
|
2
|
+
export { default as BigNumber } from 'bignumber.js';
|
|
3
|
+
export type BN = BigNumber;
|
|
4
|
+
export declare const bn: (n: BigNumber.Value, base?: number) => BN;
|
|
5
|
+
export declare const bnOrZero: (n: BigNumber.Value | null | undefined) => BN;
|
|
6
|
+
export declare const positiveOrZero: (n: BigNumber.Value | null | undefined) => BN;
|
|
7
|
+
export declare const convertPrecision: ({ value, inputExponent, outputExponent, }: {
|
|
8
|
+
value: BigNumber.Value;
|
|
9
|
+
inputExponent?: number | undefined;
|
|
10
|
+
outputExponent?: number | undefined;
|
|
11
|
+
}) => BigNumber;
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import BigNumber from 'bignumber.js';
|
|
2
|
+
export { default as BigNumber } from 'bignumber.js';
|
|
3
|
+
export const bn = (n, base = 10) => new BigNumber(n, base);
|
|
4
|
+
export const bnOrZero = (n) => {
|
|
5
|
+
const value = bn(n || 0);
|
|
6
|
+
return value.isFinite() ? value : bn(0);
|
|
7
|
+
};
|
|
8
|
+
export const positiveOrZero = (n) => {
|
|
9
|
+
const value = bn(n || 0);
|
|
10
|
+
return value.isPositive() ? value : bn(0);
|
|
11
|
+
};
|
|
12
|
+
export const convertPrecision = ({ value, inputExponent = 0, outputExponent = 0, }) => {
|
|
13
|
+
return bnOrZero(value)
|
|
14
|
+
.dividedBy(bn(10).exponentiatedBy(inputExponent))
|
|
15
|
+
.multipliedBy(bn(10).exponentiatedBy(outputExponent));
|
|
16
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import { describe, expect, it } from 'vitest';
|
|
2
|
+
import { BigNumber, bn, bnOrZero, convertPrecision } from './bignumber.js';
|
|
3
|
+
describe('bignumber', () => {
|
|
4
|
+
describe('bnOrZero', () => {
|
|
5
|
+
it('returns an instance of bignumber', () => {
|
|
6
|
+
const zero = bnOrZero(0);
|
|
7
|
+
expect(zero).toBeInstanceOf(BigNumber);
|
|
8
|
+
const one = bnOrZero(1);
|
|
9
|
+
expect(one).toBeInstanceOf(BigNumber);
|
|
10
|
+
const foo = bnOrZero('foo');
|
|
11
|
+
expect(foo).toBeInstanceOf(BigNumber);
|
|
12
|
+
expect(foo.toString()).toBe('0');
|
|
13
|
+
const empty = bnOrZero('');
|
|
14
|
+
expect(empty).toBeInstanceOf(BigNumber);
|
|
15
|
+
expect(empty.toString()).toBe('0');
|
|
16
|
+
});
|
|
17
|
+
});
|
|
18
|
+
describe('convertPrecision', () => {
|
|
19
|
+
it('can convert values for increased precision', () => {
|
|
20
|
+
const value = '1234';
|
|
21
|
+
const expectation = bn('1234000');
|
|
22
|
+
const result = convertPrecision({ value, inputExponent: 3, outputExponent: 6 });
|
|
23
|
+
expect(result).toEqual(expectation);
|
|
24
|
+
});
|
|
25
|
+
it('can convert values for decreased precision', () => {
|
|
26
|
+
const value = '1234000';
|
|
27
|
+
const expectation = bn('1234');
|
|
28
|
+
const result = convertPrecision({ value, inputExponent: 6, outputExponent: 3 });
|
|
29
|
+
expect(result).toEqual(expectation);
|
|
30
|
+
});
|
|
31
|
+
it('treats 0 as 0 when increasing precision', () => {
|
|
32
|
+
const value = '0';
|
|
33
|
+
const expectation = bn('0');
|
|
34
|
+
const result = convertPrecision({ value, inputExponent: 12, outputExponent: 18 });
|
|
35
|
+
expect(result).toEqual(expectation);
|
|
36
|
+
});
|
|
37
|
+
it('treats 0 as 0 when decreasing precision', () => {
|
|
38
|
+
const value = '0';
|
|
39
|
+
const expectation = bn('0');
|
|
40
|
+
const result = convertPrecision({ value, inputExponent: 18, outputExponent: 12 });
|
|
41
|
+
expect(result).toEqual(expectation);
|
|
42
|
+
});
|
|
43
|
+
it('does not remove decimals with rounding', () => {
|
|
44
|
+
const value = '1234567';
|
|
45
|
+
const expectation = bn('1234.567');
|
|
46
|
+
const result = convertPrecision({ value, inputExponent: 6, outputExponent: 3 });
|
|
47
|
+
expect(result).toEqual(expectation);
|
|
48
|
+
});
|
|
49
|
+
});
|
|
50
|
+
});
|