Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
116 changes: 79 additions & 37 deletions API.md
Original file line number Diff line number Diff line change
Expand Up @@ -33,8 +33,8 @@
- [listAccessPages](#listaccesspages)
- [revokeAccess](#revokeaccess)
- [IndexerClient](#indexerclient)
- [getTokenBalances](#gettokenbalances)
- [getNativeTokenBalance](#getnativetokenbalance)
- [getBalances](#getbalances)
- [getTransactionHistory](#gettransactionhistory)
- [Errors](#errors)
- [Types](#types)
- [Network](#network)
Expand All @@ -55,7 +55,8 @@
- [SendTransactionResponse](#sendtransactionresponse)
- [TransactionStatusPollingOptions](#transactionstatuspollingoptions)
- [FeeOptionSelector](#feeoptionselector)
- [TokenBalancesResult](#tokenbalancesresult)
- [BalancesResult](#balancesresult)
- [TransactionHistoryResult](#transactionhistoryresult)
- [TokenBalancesPage](#tokenbalancespage)
- [TokenBalance](#tokenbalance)
- [TokenContractInfo](#tokencontractinfo)
Expand Down Expand Up @@ -96,7 +97,7 @@ new OMSClient(params: {

| Name | Type | Required | Description |
|---|---|---|---|
| `publishableKey` | `string` | Yes | Your OMS publishable key. |
| `publishableKey` | `string` | Yes | Your OMS publishable key. Wallet and IndexerGateway requests send this as the `Api-Key` header. |
| `projectId` | `string` | Yes | Your OMS project ID. Used as the WaaS signing scope for wallet requests and OIDC redirect state. |
| `environment` | `OmsEnvironment` | No | API endpoint configuration. Defaults to the SDK's configured OMS endpoints. |
| `storage` | `StorageManager` | No | Storage backend for wallet metadata. Defaults to `LocalStorageManager` when browser `localStorage` is available, otherwise `MemoryStorageManager`. |
Expand Down Expand Up @@ -700,66 +701,83 @@ if (other) {

## IndexerClient

Accessed via `oms.indexer`. Queries on-chain token balances through the OMS Indexer API.
Accessed via `oms.indexer`. Queries on-chain balances and transaction history through IndexerGateway.

### getTokenBalances
### getBalances

```typescript
getTokenBalances(params: {
network: Network
contractAddress?: string
getBalances(params: {
walletAddress: string
includeMetadata: boolean
page?: {
page?: number
pageSize?: number
}
}): Promise<TokenBalancesResult>
networks?: Network[]
networkType?: 'MAINNETS' | 'TESTNETS' | 'ALL'
contractAddresses?: string[]
includeMetadata?: boolean
omitPrices?: boolean
tokenIds?: string[]
page?: TokenBalancesPage
}): Promise<BalancesResult>
```

Fetches token balances for a wallet on a given network. Omit `contractAddress` to query balances across contracts; provide it to filter to one token contract. The default request returns page `0` with up to `40` entries. When `includeMetadata` is `true`, token display data is returned on `contractInfo` and `tokenMetadata`; ERC-20 decimals are available as `contractInfo.decimals`.
Fetches native and token balances for a wallet. Pass `networks` to query explicit SDK network objects. If `networks` is omitted, the request defaults to `networkType: 'MAINNETS'`. The default request returns page `0` with up to `40` entries. `includeMetadata` defaults to `true`; token display data is returned on `contractInfo` and `tokenMetadata`, and ERC-20 decimals are available as `contractInfo.decimals`.

**Parameters**

| Name | Type | Description |
|---|---|---|
| `network` | `Network` | The network to query. Use an exported registry value such as `Networks.polygon`. |
| `contractAddress` | `string` | Optional token contract filter. Omit to query balances across contracts. |
| `walletAddress` | `string` | The wallet address whose balances to fetch. Use `oms.wallet.walletAddress` after checking it is defined. |
| `includeMetadata` | `boolean` | When `true`, the response includes token metadata such as name, symbol, and decimals. |
| `page` | `{ page?: number; pageSize?: number }` | Optional pagination request. Defaults to `{ page: 0, pageSize: 40 }`. |
| `networks` | `Network[]` | Optional explicit networks to query. Use exported registry values such as `Networks.polygon`. |
| `networkType` | `'MAINNETS' \| 'TESTNETS' \| 'ALL'` | Optional gateway network group when `networks` is omitted. Defaults to `'MAINNETS'`. |
| `contractAddresses` | `string[]` | Optional token contract filter. Omit to query balances across contracts. |
| `includeMetadata` | `boolean` | Optional metadata flag. Defaults to `true`. |
| `omitPrices` | `boolean` | Optional price exclusion flag. |
| `tokenIds` | `string[]` | Optional token ID filter. |
| `page` | `TokenBalancesPage` | Optional pagination request. Defaults to `{ page: 0, pageSize: 40 }`. |

**Returns** `Promise<TokenBalancesResult>` — see [TokenBalancesResult](#tokenbalancesresult).
**Returns** `Promise<BalancesResult>` — see [BalancesResult](#balancesresult).

**Example**

```typescript
const { walletAddress } = oms.wallet
if (!walletAddress) throw new Error('No active wallet session')

const result = await oms.indexer.getTokenBalances({
network: Networks.polygon,
const result = await oms.indexer.getBalances({
networks: [Networks.polygon],
walletAddress,
includeMetadata: true,
})

for (const b of result.nativeBalances) {
console.log(b.symbol, b.balance)
}

for (const b of result.balances) {
console.log(b.contractAddress, b.balance, b.tokenId)
}
```

---

### getNativeTokenBalance
### getTransactionHistory

```typescript
getNativeTokenBalance(params: {
network: Network
getTransactionHistory(params: {
walletAddress: string
}): Promise<TokenBalance | undefined>
networks?: Network[]
networkType?: 'MAINNETS' | 'TESTNETS' | 'ALL'
contractAddresses?: string[]
transactionHashes?: string[]
metaTransactionIds?: string[]
fromBlock?: number
toBlock?: number
tokenId?: string
includeMetadata?: boolean
omitPrices?: boolean
page?: TokenBalancesPage
}): Promise<TransactionHistoryResult>
```

Fetches the native token balance for a wallet. This is also used internally to enrich transaction fee options.
Fetches mined transaction history for a wallet. Pass `networks` to query explicit SDK network objects. If `networks` is omitted, the request defaults to `networkType: 'MAINNETS'`. `includeMetadata` defaults to `true`.

---

Expand Down Expand Up @@ -874,7 +892,7 @@ findNetworkByName(name: string): Network | undefined
```typescript
interface OmsEnvironment {
walletApiUrl: string
indexerUrlTemplate: string
indexerGatewayUrl: string
auth?: {
oidcProviders?: Record<string, OidcProviderConfig>
}
Expand All @@ -884,10 +902,10 @@ interface OmsEnvironment {
| Field | Type | Description |
|---|---|---|
| `walletApiUrl` | `string` | Base URL of the WaaS Wallet RPC host. |
| `indexerUrlTemplate` | `string` | URL template for the Indexer API. `{value}` is replaced with the selected network name, e.g. `"https://indexer.example.com/{value}"`. |
| `indexerGatewayUrl` | `string` | Base URL of the IndexerGateway host, e.g. `"https://api.example.com/v1/IndexerGateway/"`. |
| `auth.oidcProviders` | `Record<string, OidcProviderConfig>` | OIDC provider configurations addressable by provider key. |

The default is exported as `defaultOmsEnvironment` and includes the `google` OIDC provider.
The default is exported as `defaultOmsEnvironment`, uses `https://sandbox-api.dev.polygon-dev.technology` as the WaaS API base URL, and includes the `google` OIDC provider.

Use `defineOmsEnvironment` to preserve typed custom OIDC provider keys:

Expand Down Expand Up @@ -1182,12 +1200,13 @@ that fee option.

---

### TokenBalancesResult
### BalancesResult

```typescript
interface TokenBalancesResult {
interface BalancesResult {
status: number
page?: TokenBalancesPage
nativeBalances: TokenBalance[]
balances: TokenBalance[]
}
```
Expand All @@ -1196,25 +1215,48 @@ interface TokenBalancesResult {
|---|---|---|
| `status` | `number` | HTTP status code of the indexer response. |
| `page` | `TokenBalancesPage` | Pagination metadata, if present. |
| `nativeBalances` | `TokenBalance[]` | Native token balances for the requested address. |
| `balances` | `TokenBalance[]` | Array of token balance entries for the requested address. |

---

### TransactionHistoryResult

```typescript
interface TransactionHistoryResult {
status: number
page?: TokenBalancesPage
transactions: Transaction[]
}
```

| Field | Type | Description |
|---|---|---|
| `status` | `number` | HTTP status code of the indexer response. |
| `page` | `TokenBalancesPage` | Pagination metadata, if present. |
| `transactions` | `Transaction[]` | Flattened transaction entries across the requested networks. |

---

### TokenBalancesPage

```typescript
interface TokenBalancesPage {
page: number
pageSize: number
more: boolean
page?: number
pageSize?: number
more?: boolean
before?: unknown
after?: unknown
}
```

| Field | Type | Description |
|---|---|---|
| `page` | `number` | Current page index (zero-based). |
| `pageSize` | `number` | Number of entries per page (up to 40). |
| `pageSize` | `number` | Number of entries per page. |
| `more` | `boolean` | `true` if additional pages are available. |
| `before` | `unknown` | Gateway cursor before the current page, when returned. |
| `after` | `unknown` | Gateway cursor after the current page, when returned. |

---

Expand Down
25 changes: 12 additions & 13 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,8 @@ const oms = new OMSClient({
})
```

By default, wallet requests use the sandbox WaaS API at `https://sandbox-api.dev.polygon-dev.technology`.

In Vite browser apps, keep those values in local environment variables:

```typescript
Expand Down Expand Up @@ -424,12 +426,12 @@ const oms = new OMSClient({
projectId: 'your-project-id',
environment: {
walletApiUrl: 'https://staging-wallet.example.com',
indexerUrlTemplate: 'https://staging-indexer.example.com/{value}',
indexerGatewayUrl: 'https://staging-indexer.example.com/v1/IndexerGateway/',
},
})
```

For indexer requests, `{value}` is replaced with the selected `Network.name`, such as `polygon` or `amoy`.
For indexer requests, `indexerGatewayUrl` points at the IndexerGateway base URL.

### Custom Storage and Signing

Expand Down Expand Up @@ -497,31 +499,28 @@ const tx = await oms.wallet.callContract({
})
```

### Query Token and Native Balances
### Query Balances

```typescript
const { walletAddress } = oms.wallet
if (!walletAddress) throw new Error('No active wallet session')

const result = await oms.indexer.getTokenBalances({
network: Networks.polygon,
const result = await oms.indexer.getBalances({
networks: [Networks.polygon],
walletAddress,
includeMetadata: true,
})

for (const b of result.nativeBalances) {
console.log(b.symbol, b.balance)
}

for (const b of result.balances) {
console.log(b.contractInfo?.symbol, b.balance, b.contractInfo?.decimals)
}

const nativeBalance = await oms.indexer.getNativeTokenBalance({
network: Networks.polygon,
walletAddress,
})

console.log(nativeBalance?.balance)
```

Pass `contractAddress` to filter balances to one token contract. With `includeMetadata: true`, ERC-20 decimals are available as `contractInfo.decimals`. The response is paginated; pass `page` when requesting later pages.
Pass `contractAddresses` to filter balances to specific token contracts. Omit `networks` to query mainnets by default, or pass `networkType: 'TESTNETS'` / `'ALL'`. With `includeMetadata: true`, ERC-20 decimals are available as `contractInfo.decimals`. The response is paginated; pass `page` when requesting later pages.

### Manage Access

Expand Down
4 changes: 2 additions & 2 deletions docs/error-contracts.md
Original file line number Diff line number Diff line change
Expand Up @@ -33,8 +33,8 @@ supports, whether `upstreamError` should be present, and which test owns the con
| `oms.wallet.sendTransaction`, `callContract` | Submitted transaction status polling fails | `OmsTransactionError`, `OMS_TRANSACTION_STATUS_LOOKUP_FAILED`, `retryable: true`, `txnId` | Retry status lookup, not the original write | Present when polling crossed transport/upstream boundary | `snapshots transaction status polling failures with txn and upstream details`; `snapshots transaction status polling backend errors as retryable` |
| `oms.wallet.getTransactionStatus` | Direct status lookup backend failure | `OmsRequestError` or `OmsResponseError` with status operation | Retry status lookup or surface backend status to the user | Present | `snapshots direct transaction status backend errors with upstream details` |
| `oms.wallet.listAccess`, `listAccessPages`, `revokeAccess` | WaaS access backend failure | `OmsRequestError` or `OmsResponseError` with access operation | Retry based on SDK code/status; log upstream detail | Present | `snapshots access backend errors with upstream details` |
| `oms.indexer.getTokenBalances`, `getNativeTokenBalance` | Indexer backend, transport, malformed JSON, or malformed payload | `OmsRequestError` or `OmsResponseError` with indexer operation | Retry based on SDK code/status; log upstream detail | Present for remote/transport response failures | `snapshots indexer backend errors with upstream details`; `snapshots native balance indexer errors with upstream details`; `snapshots indexer transport failures with upstream details`; `snapshots indexer malformed response errors with upstream details` |
| `oms.indexer.getTokenBalances`, `getNativeTokenBalance` | Indexer non-JSON HTTP body | `OmsRequestError`, `OMS_HTTP_ERROR`, sanitized message | Do not expose raw upstream HTML/text bodies; log normalized detail | Present, sanitized | `snapshots indexer non-JSON HTTP errors without raw upstream bodies` |
| `oms.indexer.getBalances`, `getTransactionHistory` | Indexer backend, transport, malformed JSON, or malformed payload | `OmsRequestError` or `OmsResponseError` with indexer operation | Retry based on SDK code/status; log upstream detail | Present for remote/transport response failures | `snapshots indexer backend errors with upstream details`; `snapshots transaction history indexer errors with upstream details`; `snapshots indexer transport failures with upstream details`; `snapshots indexer malformed response errors with upstream details` |
| `oms.indexer.getBalances`, `getTransactionHistory` | Indexer non-JSON HTTP body | `OmsRequestError`, `OMS_HTTP_ERROR`, sanitized message | Do not expose raw upstream HTML/text bodies; log normalized detail | Present, sanitized | `snapshots indexer non-JSON HTTP errors without raw upstream bodies` |
| Exported storage managers and credential signers | Local runtime capability or storage failure | Native `Error` or signer/storage-specific runtime error | Fix local runtime support or storage availability | Absent | `snapshots exported storage and signer runtime errors` |
| Exported `OmsSdkError` classes and `isOmsSdkError` | Error class/helper field contract | Stable public fields on constructed errors | Use only when the error class/helper is the unit under test | As constructed | `snapshots exported error helper and subclass fields` |

Expand Down
4 changes: 2 additions & 2 deletions examples/trails-actions/.env.example
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
VITE_OMS_PUBLISHABLE_KEY=
VITE_OMS_PROJECT_ID=
VITE_OMS_PUBLISHABLE_KEY=your-publishable-key
VITE_OMS_PROJECT_ID=your-oms-project-id
24 changes: 11 additions & 13 deletions examples/trails-actions/src/trailsActions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -183,20 +183,18 @@ export function requirePreparedYieldTransactions(
}

export async function getPolygonBalances(walletAddress: Address): Promise<BalanceState> {
const [polBalance, usdcResult] = await Promise.all([
oms.indexer.getNativeTokenBalance({
network: POLYGON_NETWORK,
walletAddress,
}),
oms.indexer.getTokenBalances({
network: POLYGON_NETWORK,
contractAddress: POLYGON_USDC,
walletAddress,
includeMetadata: false,
}),
])
const balances = await oms.indexer.getBalances({
networks: [POLYGON_NETWORK],
contractAddresses: [POLYGON_USDC],
walletAddress,
includeMetadata: false,
})
const polBalance = balances.nativeBalances.find(balance => balance.chainId === POLYGON_NETWORK.id)
const usdcBalance = balances.balances.find(balance =>
balance.contractAddress?.toLowerCase() === POLYGON_USDC.toLowerCase(),
)
const polRaw = polBalance?.balance ?? '0'
const usdcRaw = usdcResult.balances[0]?.balance ?? '0'
const usdcRaw = usdcBalance?.balance ?? '0'

return {
pol: formatTokenAmount(polRaw, 18, 'POL'),
Expand Down
Loading
Loading