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

# Solana Asset Search: Find NFTs, Tokens & Compressed Assets

> Use the searchAssets endpoint to discover NFTs, compressed assets, and fungible tokens on Solana, with advanced filtering, sorting, and pagination.

## Overview

`searchAssets` is the most flexible read method in the DAS API. It returns assets that match a combination of filters — owner, collection grouping, token type, and attributes — in a single paginated call. Use it whenever you need more than a single asset or a plain by-owner list.

`tokenType` is optional. When omitted, `searchAssets` returns regular and compressed NFTs only — no fungible tokens. To include fungible tokens, set `tokenType` (for example, `"fungible"` or `"all"`). Accepted values are `fungible`, `nonFungible`, `regularNft`, `compressedNft`, and `all`.

## When to use this

Use `searchAssets` when you are:

* Filtering a wallet's assets to just fungible tokens or just NFTs
* Listing the assets a wallet owns within a specific collection
* Discovering compressed NFTs in bulk
* Building infinite scroll over large result sets with cursor pagination
* Filtering MPL Core assets by agent status or signer

For single assets use [`getAsset`](/api-reference/das/getasset); for a plain wallet listing use [`getAssetsByOwner`](/api-reference/das/getassetsbyowner).

<Card title="API Reference" horizontal icon="code" href="/api-reference/das/searchassets">
  View detailed documentation for searchAssets
</Card>

## Quickstart

```typescript theme={"system"}
// Replace YOUR_API_KEY with your Helius API key
const url = `https://mainnet.helius-rpc.com/?api-key=YOUR_API_KEY`;

async function searchAssets(params) {
  const body = {
    jsonrpc: "2.0",
    id: "search-assets-example",
    method: "searchAssets",
    params,
  };
  const res = await fetch(url, {
    method: "POST",
    headers: { "Content-Type": "application/json" },
    body: JSON.stringify(body),
  });
  if (!res.ok) {
    throw new Error(`${res.status} ${res.statusText}`);
  }
  const { result } = await res.json();
  return result;
}

// Example: fetch first 50 compressed NFTs in a wallet
searchAssets({
  ownerAddress: "86xCnPeV69n6t3DnyGvkKobf9FdN2H9oiVDdaMpo2MMY",
  tokenType: "compressedNft",
  limit: 50,
}).then(console.log);
```

## Choosing a tokenType

`tokenType` is optional and specifies **what kind of assets** appear in the response. When omitted, `searchAssets` returns regular and compressed NFTs only — set `tokenType` to include fungible tokens.

<ParamField body="tokenType" type="string">
  Accepted values: `fungible`, `nonFungible`, `regularNft`, `compressedNft`, `all`. Defaults to regular and compressed NFTs when omitted.
</ParamField>

| tokenType       | What you get                      | Typical use case              |
| --------------- | --------------------------------- | ----------------------------- |
| `fungible`      | SPL and Token-2022 tokens only    | Wallet balances, token-gating |
| `nonFungible`   | All NFTs (compressed and regular) | Portfolio overview            |
| `regularNft`    | Legacy and pNFTs (uncompressed)   | Marketplace listings          |
| `compressedNft` | cNFTs only                        | Ultra-cheap mass mints        |
| `all`           | Everything (tokens and NFTs)      | Catch-all discovery           |

## Pagination and sorting

Solana wallets can own thousands of assets, so efficient paging matters:

* **Page / limit** — classic pagination (`page` starts at **1**). Good for static views.
* **Cursor** — pass `before` or `after` values from the previous response for fast, infinite scrolling.

```json5 sortBy theme={"system"}
"sortBy": {
  "sortBy": "created",      // created | recent_action | updated | none
  "sortDirection": "desc"   // asc | desc
}
```

For full page/limit and cursor strategies, including parallel keyset querying, see the [Pagination guide](/das/pagination).

## Display options

These flags **add metadata**; they never change which assets are returned.

| Flag                     | Effect                                 |
| ------------------------ | -------------------------------------- |
| `showNativeBalance`      | Includes the SOL balance of the wallet |
| `showCollectionMetadata` | Adds collection-level JSON data        |
| `showGrandTotal`         | Returns the total match count (slower) |

```json5 options theme={"system"}
"options": {
  "showNativeBalance": true,
  "showCollectionMetadata": true,
  "showGrandTotal": true
}
```

## MPL Core agents, asset signers, and MIP-11 groups

MPL Core assets can expose **agent identity** and **asset-signer** metadata, and assets or collections may include a **`groups` plugin** (MIP-11) describing group membership. The same optional fields appear on every asset-returning DAS method (`getAsset`, `getAssetBatch`, `getAssetsByOwner`, `getAssetsByGroup`, `getAssetsByCreator`, `getAssetsByAuthority`, and each item in `searchAssets`).

Use `searchAssets` to filter by agent status or addresses:

| Parameter     | Type    | Purpose                            |
| ------------- | ------- | ---------------------------------- |
| `isAgent`     | boolean | Only assets with an Agent Identity |
| `agentToken`  | string  | Match agent token mint (base58)    |
| `assetSigner` | string  | Match asset-signer PDA (base58)    |

You can also set `interface` to `MplCoreAsset`, `MplCoreCollection`, or `MplCoreGroup` for MPL Core–specific discovery.

```json theme={"system"}
{
  "jsonrpc": "2.0",
  "id": "1",
  "method": "searchAssets",
  "params": {
    "ownerAddress": "86xCnPeV69n6t3DnyGvkKobf9FdN2H9oiVDdaMpo2MMY",
    "tokenType": "all",
    "isAgent": true,
    "page": 1,
    "limit": 10
  }
}
```

The response fields `is_agent`, `agent_token`, and `asset_signer` are **omitted when not applicable** (for example, `is_agent` is omitted when false). See the [searchAssets API reference](/api-reference/das/searchassets) for full schemas.

## Examples

The first example shows the full `fetch` wrapper. The remaining examples follow the same pattern and are collapsed — expand them for the request body.

### Search for all fungible tokens in a wallet

```typescript theme={"system"}
const url = `https://mainnet.helius-rpc.com/?api-key=YOUR_API_KEY`

const searchAssets = async () => {
  const response = await fetch(url, {
    method: 'POST',
    headers: {
      'Content-Type': 'application/json',
    },
    body: JSON.stringify({
      jsonrpc: '2.0',
      id: 'my-id',
      method: 'searchAssets',
      params: {
        ownerAddress: '86xCnPeV69n6t3DnyGvkKobf9FdN2H9oiVDdaMpo2MMY',
        tokenType: 'fungible',
      },
    }),
  });
  const { result } = await response.json();
  console.log("Search Assets: ", result);
};
searchAssets();
```

<Accordion title="Search for fungible tokens with native balance and token info">
  ```typescript theme={"system"}
  const url = `https://mainnet.helius-rpc.com/?api-key=YOUR_API_KEY`

  const searchAssetsTokenInfo = async () => {
      const response = await fetch(url, {
          method: 'POST',
          headers: {
              'Content-Type': 'application/json',
          },
          body: JSON.stringify({
              jsonrpc: '2.0',
              id: 'my-id',
              method: 'searchAssets',
              params: {
                  ownerAddress: '86xCnPeV69n6t3DnyGvkKobf9FdN2H9oiVDdaMpo2MMY',
                  tokenType: 'fungible',
                  options: {
                      showNativeBalance: true,
                  },
              },
          }),
      });

      const { result } = await response.json();

      result.items.forEach(item => {
        console.log(item.token_info);
      });

      console.log("Native Balance: ", result.nativeBalance);
  };

  searchAssetsTokenInfo();
  ```
</Accordion>

<Accordion title="Search for Drip NFTs owned by vibhu.sol">
  ```typescript theme={"system"}
  const url = `https://mainnet.helius-rpc.com/?api-key=YOUR_API_KEY`

  const searchAssetsDrip = async () => {
    const response = await fetch(url, {
      method: 'POST',
      headers: {
        'Content-Type': 'application/json',
      },
      body: JSON.stringify({
        jsonrpc: '2.0',
        id: 'my-id',
        method: 'searchAssets',
        params: {
          ownerAddress: 'BAVjpySHMMGDpq3whU7qaqCCRE8ksCeGwxa53Qv2i8jS',
          grouping: ["collection", "DRiP2Pn2K6fuMLKQmt5rZWyHiUZ6WK3GChEySUpHSS4x"],
          page: 1,
          limit: 1000
        },
      }),
    });
    const { result } = await response.json();
    console.log("Drip Haus Assets: ", result);
  };
  searchAssetsDrip();
  ```
</Accordion>

<Accordion title="Search for compressed assets in a wallet">
  ```typescript theme={"system"}
  const url = `https://mainnet.helius-rpc.com/?api-key=YOUR_API_KEY`

  const searchAssetsCompressed = async () => {
    const response = await fetch(url, {
      method: 'POST',
      headers: {
        'Content-Type': 'application/json',
      },
      body: JSON.stringify({
        jsonrpc: '2.0',
        id: 'my-id',
        method: 'searchAssets',
        params: {
          ownerAddress: '2k5AXX4guW9XwRQ1AKCpAuUqgWDpQpwFfpVFh3hnm2Ha',
          compressed: true,
        },
      }),
    });
    const { result } = await response.json();
    console.log("Search Assets: ", result);
  };
  searchAssetsCompressed();
  ```
</Accordion>

## Next steps

<CardGroup cols={3}>
  <Card title="Pagination" icon="list" href="/das/pagination">
    Page-based and keyset pagination for large result sets.
  </Card>

  <Card title="Fungible Token Extension" icon="coins" href="/das/fungible-token-extension">
    How tokenType, balances, and prices appear in results.
  </Card>

  <Card title="searchAssets reference" icon="code" href="/api-reference/das/searchassets">
    Full request and response schemas.
  </Card>
</CardGroup>
