import { CborByte, CborSet, CborUnsigned } from "."; import { AssetUtils, CardanoAsset, Multiasset } from "../assets"; import { UTXOS } from "../utxos"; const encodeCardanoAssets = (assets: CardanoAsset[], coin?: number) => { const multiasset = AssetUtils.fromAssetsToPolicyMap(assets); return encodeMultiasset(multiasset, coin); }; const encodeMultiasset = (multiasset: Multiasset, coin?: number) => { const sortedMultiasset = sort(multiasset); const encodedCoin = CborUnsigned.encode( coin ? coin : UTXOS.calculateMinMultiassetCost(sortedMultiasset) ); const policies = Object.keys(sortedMultiasset); return policies.reduce((acc, policy) => { const encodedPolicy = CborByte.encode(policy); const policyAssets = Object.keys(sortedMultiasset[policy]); const encodedAssets = policyAssets.reduce((encodedAssets, assetName) => { const encodedAssetName = CborByte.encode(assetName); const quantity = (sortedMultiasset[policy] as Multiasset)[ assetName ] as number; const encodedQuantity = CborUnsigned.encode(quantity); return `${encodedAssets}${encodedAssetName}${encodedQuantity}`; }, CborSet.sizeToCbor(policyAssets.length)); return `${acc}${encodedPolicy}${encodedAssets}`; }, `82${encodedCoin}${CborSet.sizeToCbor(policies.length)}`); }; const encode = (value: Multiasset | CardanoAsset[], coin?: number) => { if (Array.isArray(value)) { return encodeCardanoAssets(value, coin); } else { return encodeMultiasset(value, coin); } }; const sort = (unordered: Multiasset) => { return Object.keys(unordered) .sort((k1, k2) => { if (k1.length > k2.length) return 1; else if (k2.length > k1.length) return -1; return k1 > k2 ? 1 : -1; }) .reduce((obj, key) => { obj[key] = typeof unordered[key] === "object" ? sort(unordered[key] as Multiasset) : unordered[key]; return obj; }, {} as Multiasset); }; export const CborMultiasset = { encode, sort, };