> ## Documentation Index
> Fetch the complete documentation index at: https://docs.inco.org/llms.txt
> Use this file to discover all available pages before exploring further.

# Optional indexing

> Opt into hosted history, discovery, and prices, or use your own backend.

## Opt in explicitly

Indexing is **off by default**. Enable it for history, discovery, and prices. Chain operations and Lightning encryption/attestations work independently.

```ts theme={null}
// Default: on-chain features, no indexer requests.
const ctoken = new CTokenClient({ network: "baseSepolia", publicClient, walletClient });

// Opt in to Inco's hosted Base Sepolia service.
const withHistory = new CTokenClient({
  network: "baseSepolia", publicClient, walletClient, indexer: true,
});

// Opt in to your compatible service. The URL is a base prefix, not a route.
const custom = new CTokenClient({
  network: "baseSepolia", publicClient, walletClient,
  indexer: { url: "https://your-indexer.example/api", timeoutMs: 15_000 },
});
```

```tsx theme={null}
<CTokenProvider network="baseSepolia" publicClient={publicClient} indexer>
  <ConfidentialWallet />
</CTokenProvider>

<CTokenProvider network="baseSepolia" publicClient={publicClient}
  indexer={{ url: "https://your-indexer.example/api" }}>
  <ConfidentialWallet />
</CTokenProvider>
```

`false`/omitted: off. `true`/`{}`: hosted service for the selected network. `{ url }`: your compatible service.

When off, widgets hide history/discovery and retain configured tokens and chain balances. History/assets hooks do not auto-fetch; direct calls and manual refetches raise `INDEXER_NOT_CONFIGURED`. Custom UI can check `Boolean(useCToken().context.indexerUrl)`.

## Three HTTP-backed methods

| SDK call                                        | HTTP request                         | Defaults                                                                                    |
| ----------------------------------------------- | ------------------------------------ | ------------------------------------------------------------------------------------------- |
| `history({ address?, page?, limit?, signal? })` | GET `/wallets/:address/transactions` | Current owner, page 1, limit 10; integer limit 1–100.                                       |
| `assets({ address?, signal? })`                 | GET `/wallets/:address/assets`       | Current owner; unpaginated.                                                                 |
| `prices(tokens?, { signal }?)`                  | GET `/prices?tokens=...`             | Empty/omitted tokens means the indexer's available priced set; at most 200 input addresses. |

An explicit address allows history/assets without a wallet. Missing prices remain absent, never zero.

```ts theme={null}
const controller = new AbortController();
const page = await ctoken.history({
  address: owner, page: 2, limit: 20, signal: controller.signal,
});
const prices = await ctoken.prices([USDC], { signal: controller.signal });
const usd = prices.prices[USDC.toLowerCase()]?.usd;
// controller.abort() cancels outstanding requests using this signal.
```

## Asset

| Field                 | Type                | Meaning                                            |
| --------------------- | ------------------- | -------------------------------------------------- |
| `address`             | string address      | cToken contract.                                   |
| `base_erc20`          | string address      | Underlying token.                                  |
| `name`, `symbol`      | string              | Indexed wrapper metadata.                          |
| `decimals`            | number              | Token precision.                                   |
| `balance_handle`      | 32-byte hex or null | Encrypted balance handle; not a plaintext balance. |
| `handle_block`        | string or null      | Block associated with handle update.               |
| `last_activity_block` | string              | Most recent indexed activity.                      |

Indexed holdings do not prove a spendable balance. Read and decrypt chain state for exact amounts.

## Tx and TxPage

```ts theme={null}
type TxPage = {
  items: Tx[];
  total: number;
  page: number;
  pages: number;
  limit: number;
};

type Tx = {
  type: "transfer" | "flow";
  token: string;             // cToken
  symbol: string;
  decimals: number;
  kind: string;
  from_addr: string | null;
  to_addr: string | null;
  handle: string | null;
  amount: string | null;     // integer base units, public flow only
  block_number: string;
  block_time?: string;      // Unix seconds; raw API null becomes undefined
  log_index?: number;
  tx_hash: string;
};
```

Transfers expose handles with null amounts; flows expose base-unit amount strings. History excludes zero-address confidential mint/burn legs and public `burn` rows, ordered by descending block/log index.

## Prices

```ts theme={null}
type Prices = {
  chainId: number;
  ttl: number;               // seconds
  count: number;
  prices: Record<string, {
    usd: number;
    confidence: number | null;
    source: string;
    updated_at: number;     // Unix seconds
    stale: boolean;
  }>;
};
```

Display the `stale` flag. Missing quotes are unknown. Keys are lowercase underlying addresses; testnet assets may use mainnet price references.

<Card title="Build a compatible indexer" icon="server" href="/ctoken/custom-indexer">Implement the three SDK routes with the exact schemas and pagination rules.</Card>
