diff --git a/CHANGELOG.md b/CHANGELOG.md index 7aa8240239..6fcad452cb 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,9 @@ +## [4.2.23] - 2024.4.10 + +### Updated + +- Improved `getBalance` method in `address` module by introducing `tokenTypes` filter along with `native` option. + ## [4.2.22] - 2024.4.10 ### Fixed diff --git a/package.json b/package.json index cc86792961..e1f7accf9d 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@tatumio/tatum", - "version": "4.2.22", + "version": "4.2.23", "description": "Tatum JS SDK", "author": "Tatum", "repository": "https://github.com/tatumio/tatum-js", diff --git a/src/api/api.dto.ts b/src/api/api.dto.ts index 5c764b8604..f13c8db6ed 100644 --- a/src/api/api.dto.ts +++ b/src/api/api.dto.ts @@ -1,9 +1,11 @@ import { DefaultParamsType } from '../connector/connector.dto' import { Network } from '../dto' -export type TokenType = 'native' | 'fungible' | 'nft' | 'multitoken' +export type NftTokenType = 'nft' | 'multitoken' +export type TokenType = NftTokenType | 'fungible' +export type TokenTypeWithNative = TokenType | 'native' +export type TxType = TokenTypeWithNative | 'internal' export type TxSubtype = 'incoming' | 'outgoing' | 'zero-transfer' -export type TxType = 'fungible' | 'nft' | 'multitoken' | 'native' | 'internal' export type Chain = | 'ethereum' @@ -73,7 +75,7 @@ export interface ApiBalanceRequest extends DefaultParamsType { /** * Optional. Token types */ - tokenTypes?: 'nft' | 'multitoken' | 'fungible' | string + tokenTypes?: TokenType | string /** * Optional. The option to exclude metadata from the response. @@ -100,7 +102,7 @@ export interface ApiBalanceResponse { /** * Token type */ - type: 'native' | 'fungible' | 'nft' | 'multitoken' + type: TokenTypeWithNative /** * Address @@ -159,7 +161,7 @@ export interface ApiMetadataResponse { /** * Token type */ - tokenType: 'native' | 'fungible' | 'nft' | 'multitoken' + tokenType: TokenTypeWithNative /** * Metadata URL of the token. This data doesn't have to be present. The safest way to obtain them in that case is from the NFT Contract.tokenURI() method call. @@ -189,7 +191,7 @@ export interface ApiCollectionsRequest extends DefaultParamsType { * Use nft (includes ERC-721 and ERC-1155) or multitoken (ERC-1155 only). * */ - tokenTypes?: 'nft' | 'multitoken' + tokenTypes?: NftTokenType /** * The option to exclude metadata from the response. */ @@ -304,7 +306,7 @@ export interface ApiCollectionsResponse { chain?: Chain tokenId?: string tokenAddress?: string - tokenType?: TokenType + tokenType?: TokenTypeWithNative metadataURI?: string metadata?: object } @@ -425,7 +427,7 @@ export interface ApiTransactionsRequest extends DefaultParamsType { * Use fungible (ERC-20), nft (ERC-721 and ERC-1155), multitoken (ERC-1155), native or internal. * */ - transactionTypes?: 'fungible' | 'nft' | 'multitoken' | 'native' | 'internal' + transactionTypes?: TxType /** * The option to filter transaction based on subtype. */ @@ -749,7 +751,7 @@ export interface ApiCreateTokenRequest extends DefaultParamsType { /** * Type of the contract */ - contractType: 'fungible' | 'nft' | 'multitoken' + contractType: TokenType /** * Address of the fungible token owner */ diff --git a/src/dto/shared.dto.ts b/src/dto/shared.dto.ts index eb45143538..201aa62df4 100644 --- a/src/dto/shared.dto.ts +++ b/src/dto/shared.dto.ts @@ -1,3 +1,5 @@ +import { TokenType, TokenTypeWithNative } from '../api/api.dto' + export interface IdDto { id: string } @@ -32,6 +34,12 @@ export interface AddressBalanceFilters extends Pagination { * List of addresses to check. */ addresses: string[] + + /** + * Optional filter for token types. If not specified, all token types are returned. + * Allowed values are `native`, `fungible`, `nft` and `multitoken`. + */ + tokenTypes?: TokenTypeWithNative[] } export interface AddressBalanceFiltersTron { @@ -48,9 +56,10 @@ export interface AddressBalanceFiltersTezos extends Pagination { address: string /** - * Optional filter for token types. If not specified, all token types are returned. Allowed values are `fungible`, `nft` and `multitoken`. + * Optional filter for token types. If not specified, all token types are returned. + * Allowed values are `fungible`, `nft` and `multitoken`. */ - tokenTypes?: string[] + tokenTypes?: TokenType[] } export interface TokenDetails { @@ -65,7 +74,7 @@ export interface TokenDetails { /** * Type of the token */ - tokenType: 'fungbile' | 'nft' | 'multitoken' + tokenType: TokenType /** * Decimals of the token. Available only for `fungible` tokens */ diff --git a/src/e2e/tatum.address.spec.ts b/src/e2e/tatum.address.spec.ts index 3f52f579b8..47cbfb41b4 100644 --- a/src/e2e/tatum.address.spec.ts +++ b/src/e2e/tatum.address.spec.ts @@ -45,6 +45,21 @@ describe.skip('Address', () => { }) }) + it('should get only native balance with native assets only', async () => { + const { data } = await tatum.address.getBalance({ + addresses: ['0x514D547c8aC8ccBEc29b5144810454BD7d3625CA'], + tokenTypes: ['native'], + }) + expect(data).toHaveLength(1) + expect(data[0]).toStrictEqual({ + asset: 'ETH', + decimals: 18, + address: '0x514D547c8aC8ccBEc29b5144810454BD7d3625CA', + balance: expect.any(String), + type: 'native', + }) + }) + it('should get balance with native assets only for 2 addresses', async () => { const { data } = await tatum.address.getBalance({ addresses: [ diff --git a/src/service/address/address.dto.ts b/src/service/address/address.dto.ts index 921a6a60fc..1fe5e1d30e 100644 --- a/src/service/address/address.dto.ts +++ b/src/service/address/address.dto.ts @@ -1,3 +1,5 @@ +import { TokenTypeWithNative, TxType } from '../../api/api.dto' + export interface AddressBalance { /** * Blockchain address of the balance. @@ -18,7 +20,7 @@ export interface AddressBalance { /** * Type of the balance. */ - type: 'native' | 'fungible' | 'nft' | 'mutlitoken' + type: TokenTypeWithNative /** * Optional token contract address. Valid only for tokens (USDT, NFTs of any kind), not for native network balances (ETH, BTC). */ @@ -51,7 +53,7 @@ export interface GetAddressTransactionsQuery { /** * Optional transaction type. If not specified, all transactions are returned. For networks that support only native transactions, this parameter is ignored. */ - transactionTypes?: ['fungible' | 'nft' | 'multitoken' | 'native'] + transactionTypes?: TokenTypeWithNative[] /** * Optional transaction type. If not specified, both incoming and outgoing transactions are returned. */ @@ -161,7 +163,7 @@ export interface AddressTransaction extends AddrTxCommon { /** * Transaction type */ - transactionType: 'fungible' | 'nft' | 'multitoken' | 'native' | 'internal' + transactionType: TxType } export interface AddressTransactionUTXO extends AddrTxCommon { diff --git a/src/service/address/address.ts b/src/service/address/address.ts index 5d7d9ead26..3a6496d7bd 100644 --- a/src/service/address/address.ts +++ b/src/service/address/address.ts @@ -246,10 +246,25 @@ export class Address { page = 0, pageSize = 10, addresses, + tokenTypes, }: AddressBalanceFilters): Promise> { const chain = this.config.network return ErrorUtils.tryFail(async () => { - const nativeBalances = await this.getNativeBalance(addresses) + const result: AddressBalance[] = [] + + if (!tokenTypes || tokenTypes.includes('native')) { + const nativeBalances = await this.getNativeBalance(addresses) + result.push(...formatNativeBalances(nativeBalances, addresses, chain)) + + if (tokenTypes) { + tokenTypes = tokenTypes.filter((tokenType) => tokenType !== 'native') + } + } + + if (tokenTypes?.length === 0) { + return result + } + const tokenBalances = isDataApiEvmEnabledNetwork(chain) && (await this.connector @@ -261,17 +276,17 @@ export class Address { excludeMetadata: true, chain, addresses: addresses.join(','), + tokenTypes: tokenTypes?.join(','), }, }) .then((r) => r.result)) - const result = formatNativeBalances(nativeBalances, addresses, chain) - - if (!tokenBalances) { - return result + if (tokenBalances) { + const serializedTokenBalances = await this.processTokenBalanceDetails(tokenBalances, chain) + result.push(...serializedTokenBalances) } - const serializedTokenBalances = await this.processTokenBalanceDetails(tokenBalances, chain) - return [...result, ...serializedTokenBalances] + + return result }) } diff --git a/src/service/nft/nft.dto.ts b/src/service/nft/nft.dto.ts index 5922b2e370..21bd97be3e 100644 --- a/src/service/nft/nft.dto.ts +++ b/src/service/nft/nft.dto.ts @@ -1,3 +1,4 @@ +import { NftTokenType } from '../../api/api.dto' import { TokenIdContractAddress } from '../../dto' export interface CreateNftCollectionBase { /** @@ -129,7 +130,7 @@ export interface NftTokenDetail { /** * Token type. Either 'nft' (ERC-721) or 'multitoken' (ERC-1155) */ - type: 'nft' | 'multitoken' + type: NftTokenType /** * Token URI */ diff --git a/src/service/token/token.dto.ts b/src/service/token/token.dto.ts index 2dbdf247ab..878bcd6966 100644 --- a/src/service/token/token.dto.ts +++ b/src/service/token/token.dto.ts @@ -1,4 +1,4 @@ -import { ApiBalanceResponse, ApiTxData, FungibleInfo } from '../../api/api.dto' +import { ApiBalanceResponse, ApiTxData, FungibleInfo, TxType } from '../../api/api.dto' import { TokenAddress } from '../../dto' export interface CreateFungibleToken { @@ -144,7 +144,7 @@ export interface Transaction { /** * Transaction type */ - transactionType: 'fungible' | 'nft' | 'multitoken' | 'native' | 'internal' + transactionType: TxType /** * Transaction sub type */