> ## Documentation Index
> Fetch the complete documentation index at: https://lightprotocol-migration.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

> Retrieve all compressed accounts owned by a specific address. RPC method guide with use cases, tips and examples.

# Getcompressedaccountsbyowner

The`getCompressedAccountsByOwner` RPC method returns all compressed accounts owned by a specific address, with support for filtering, pagination, and data slicing.

<Info>
  You can test this method via the OpenAPI example or custom examples below.
</Info>

**Common Use Cases**

* **Portfolio Discovery**: Find all compressed accounts for a wallet
* **Token Account Enumeration**: Discover user's compressed token holdings
* **Account Migration**: Identify accounts to migrate from regular to compressed
* **Balance Aggregation**: Calculate total holdings across all accounts

**Parameters**

1. `owner` (PublicKey, required): Base58-encoded public key of the account owner to query compressed accounts for.
2. `options` (object, optional): Configuration object for filtering and pagination:
   * `filters` (array, optional): Array of filter objects to narrow results by specific criteria
   * `dataSlice` (object, optional): Slice of account data to return with `offset` and `length` fields
   * `cursor` (string, optional): Cursor for pagination from previous response to fetch next page
   * `limit` (BN, optional): Maximum number of accounts to return (use `bn()` helper)

**Note**: All options parameters are optional. Without filters, returns all compressed accounts for the owner.

**Response**

The response contains a paginated list of compressed accounts:

* `items` (array): Array of compressed account objects with merkle context
  * `hash` (string): Unique hash identifying the account for merkle proof generation
  * `address` (string, optional): Account address if available
  * `lamports` (number): Account balance in lamports
  * `owner` (string): Public key of the account owner
  * `data` (object): Account data information including discriminator and data hash
  * `tree` (string): Public key of the merkle tree storing this account
  * `leafIndex` (number): Position of account in the merkle tree
  * `seq` (number): Sequence number for account ordering
  * `slotCreated` (number): Slot when account was created
* `cursor` (string | null): Pagination cursor for next batch, null if no more results

**Developer Tips**

* **Pagination Strategy**: Use cursor-based pagination for owners with many accounts to avoid timeouts and ensure consistent results
* **Data Slicing Optimization**: Implement data slicing when you only need account metadata to reduce response size and improve performance
* **Empty Response Handling**: Handle cases gracefully where new addresses have no compressed accounts - this is normal behavior
* **Caching Considerations**: Cache results appropriately as compressed account states can change with each transaction
* **Batch Size**: Start with smaller batch sizes (50-100) and adjust based on response times and data needs

**Troubleshooting**

<AccordionGroup>
  <Accordion title="No accounts found">
    **Owner has no compressed accounts**

    This is normal for new addresses or those that haven't used compression:

    ```typescript theme={null}
    const accounts = await rpc.getCompressedAccountsByOwner(owner);

    if (accounts.items.length === 0) {
        console.log("No compressed accounts found for this owner");
        console.log("Create compressed accounts first using createAccountWithLamports or token operations");
    }
    ```
  </Accordion>

  <Accordion title="Request timeout with large responses">
    **Too many accounts returned at once**

    Use pagination and data slicing to reduce response size:

    ```
    const accounts = await rpc.getCompressedAccountsByOwner(owner, {
        limit: bn(50),        // Smaller batch size
        dataSlice: {          // Reduce data per account
            offset: 0,
            length: 10
        }
    });
    ```
  </Accordion>
</AccordionGroup>

**Examples**

The below examples work - just make sure you installed the dependencies.

<Accordion title="Dependencies & Setup">
  ```bash theme={null}
  npm install @lightprotocol/stateless.js @solana/web3.js
  ```

  **For Rust examples**: Requires `light-client`, `solana-sdk`, `anyhow`, and `tokio` crates. See Rust example comments for setup details.
</Accordion>

**Example: Get All Compressed Accounts**

<Tabs>
  <Tab title="TypeScript">
    ```typescript expandable theme={null}
    import { createRpc, Rpc } from '@lightprotocol/stateless.js';
    import { PublicKey } from '@solana/web3.js';

    const rpc: Rpc = createRpc(
      'https://devnet.helius-rpc.com/?api-key=YOUR_API_KEY',
      'https://devnet.helius-rpc.com/?api-key=YOUR_API_KEY'
    );

    async function getAllCompressedAccounts() {
        const owner = new PublicKey('OWNER_ADDRESS_HERE');
        const result = await rpc.getCompressedAccountsByOwner(owner);

        console.log(\`Found ${result.items.length} compressed accounts\`);

        result.items.forEach((account, index) => {
            console.log(\`Account ${index + 1}:\`);
            console.log(\`  Hash: ${account.hash.toString()}\`);
            console.log(\`  Lamports: ${account.lamports.toString()}\`);
            console.log(\`  Owner: ${account.owner.toBase58()}\`);
        });

        return result;
    }

    getAllCompressedAccounts();
    ```
  </Tab>

  <Tab title="cURL">
    ```bash theme={null}
    curl -X POST https://devnet.helius-rpc.com?api-key=YOUR_API_KEY \
      -H "Content-Type: application/json" \
      -d '{
        "jsonrpc": "2.0",
        "id": 1,
        "method": "getCompressedAccountsByOwner",
        "params": {
          "owner": "OWNER_PUBKEY_HERE"
        }
      }'
    ```
  </Tab>

  <Tab title="Rust">
    <Info>
      **Rust Client**: `light-client` v0.14.0 is available on crates.io. Use `LightClient` for the current stable API.
    </Info>

    ```rust expandable theme={null}
    // Current API: light-client 0.14.0
    use light_client::rpc::LightClient;
    use solana_sdk::pubkey::Pubkey;
    use std::str::FromStr;
    use anyhow::Result;

    #[tokio::main]
    async fn main() -> Result<()> {
        let client = LightClient::new("https://devnet.helius-rpc.com/?api-key=YOUR_API_KEY".to_string()).await?;

        // Query compressed accounts by owner
        let owner = Pubkey::from_str("OWNER_PUBKEY_HERE")?;

        match client.get_compressed_accounts_by_owner(&owner, None).await? {
            response => {
                println!("Found {} compressed accounts", response.value.items.len());

                for (index, account) in response.value.items.iter().enumerate() {
                    println!("Account {}:", index + 1);
                    println!("  Hash: {}", account.hash);
                    println!("  Lamports: {}", account.lamports);
                    println!("  Owner: {}", account.owner);
                    println!("  Tree: {}", account.tree);
                    println!("  Leaf Index: {}", account.leaf_index);
                }
            }
        }

        Ok(())
    }
    ```
  </Tab>
</Tabs>

**Example: Paginated Account Discovery with Balance Aggregation**

```typescript TypeScript expandable theme={null}
import { createRpc, bn, Rpc } from '@lightprotocol/stateless.js';
import { PublicKey } from '@solana/web3.js';

const rpc: Rpc = createRpc(
  'https://devnet.helius-rpc.com/?api-key=YOUR_API_KEY',
  'https://devnet.helius-rpc.com/?api-key=YOUR_API_KEY'
);

async function getAllAccountsPaginated(owner: PublicKey) {
    let allAccounts = [];
    let cursor = undefined;
    let totalBalance = bn(0);
    const batchSize = 100;

    do {
        const batch = await rpc.getCompressedAccountsByOwner(owner, {
            cursor,
            limit: bn(batchSize)
        });

        allAccounts.push(...batch.items);
        cursor = batch.cursor;

        // Calculate running balance
        batch.items.forEach(account => {
            totalBalance = totalBalance.add(account.lamports);
        });

        console.log(\`Fetched ${batch.items.length} accounts, total: ${allAccounts.length}\`);

        // Rate limiting
        await new Promise(resolve => setTimeout(resolve, 100));

    } while (cursor);

    console.log(\`Total compressed accounts: ${allAccounts.length}\`);
    console.log(\`Total balance: ${totalBalance.toString()} lamports\`);
    return { accounts: allAccounts, totalBalance };
}

// Usage
const owner = new PublicKey('OWNER_ADDRESS_HERE');
getAllAccountsPaginated(owner);
```

**Example: Filter by Data Slice**

```typescript expandable theme={null}
import { createRpc } from '@lightprotocol/stateless.js';
import { PublicKey } from '@solana/web3.js';

const rpc = createRpc("https://devnet.helius-rpc.com?api-key=<your-api-key>");
const owner = new PublicKey("OWNER_PUBKEY_HERE");

async function getAccountsWithDataSlice() {
    const accounts = await rpc.getCompressedAccountsByOwner(owner, {
        dataSlice: {
            offset: 0,
            length: 32  // First 32 bytes only
        }
    });

    console.log(\`Found ${accounts.items.length} accounts with data slice\`);

    accounts.items.forEach((account, index) => {
        console.log(\`Account ${index + 1}:\`);
        console.log(\`  Hash: ${account.hash.toString()}\`);
        console.log(\`  Data length: ${account.data?.data?.length || 0} bytes\`);
    });

    return accounts;
}

getAccountsWithDataSlice();
```


## OpenAPI

````yaml post /getCompressedAccountsByOwner
openapi: 3.0.3
info:
  title: photon-indexer
  description: Solana indexer for general compression
  license:
    name: Apache-2.0
  version: 0.50.0
servers:
  - url: https://devnet.helius-rpc.com?api-key=<api_key>
security: []
paths:
  /getCompressedAccountsByOwner:
    summary: getCompressedAccountsByOwner
    post:
      requestBody:
        content:
          application/json:
            schema:
              type: object
              required:
                - jsonrpc
                - id
                - method
                - params
              properties:
                id:
                  type: string
                  description: An ID to identify the request.
                  enum:
                    - test-account
                jsonrpc:
                  type: string
                  description: The version of the JSON-RPC protocol.
                  enum:
                    - '2.0'
                method:
                  type: string
                  description: The name of the method to invoke.
                  enum:
                    - getCompressedAccountsByOwner
                params:
                  type: object
                  required:
                    - owner
                  properties:
                    cursor:
                      allOf:
                        - $ref: '#/components/schemas/Hash'
                      nullable: true
                    dataSlice:
                      allOf:
                        - $ref: '#/components/schemas/DataSlice'
                      nullable: true
                    filters:
                      type: array
                      items:
                        $ref: '#/components/schemas/FilterSelector'
                    limit:
                      allOf:
                        - $ref: '#/components/schemas/Limit'
                      nullable: true
                    owner:
                      $ref: '#/components/schemas/SerializablePubkey'
                  additionalProperties: false
        required: true
      responses:
        '200':
          description: ''
          content:
            application/json:
              schema:
                type: object
                required:
                  - jsonrpc
                  - id
                properties:
                  error:
                    type: object
                    properties:
                      code:
                        type: integer
                      message:
                        type: string
                  id:
                    type: string
                    description: An ID to identify the response.
                    enum:
                      - test-account
                  jsonrpc:
                    type: string
                    description: The version of the JSON-RPC protocol.
                    enum:
                      - '2.0'
                  result:
                    type: object
                    required:
                      - context
                      - value
                    properties:
                      context:
                        $ref: '#/components/schemas/Context'
                      value:
                        $ref: '#/components/schemas/PaginatedAccountList'
                    additionalProperties: false
        '429':
          description: Exceeded rate limit.
          content:
            application/json:
              schema:
                type: object
                properties:
                  error:
                    type: object
                    properties:
                      code:
                        type: integer
                      message:
                        type: string
                  id:
                    type: string
                  jsonrpc:
                    type: string
        '500':
          description: >-
            The server encountered an unexpected condition that prevented it
            from fulfilling the request.
          content:
            application/json:
              schema:
                type: object
                properties:
                  error:
                    type: object
                    properties:
                      code:
                        type: integer
                      message:
                        type: string
                  id:
                    type: string
                  jsonrpc:
                    type: string
components:
  schemas:
    Hash:
      type: string
      description: A 32-byte hash represented as a base58 string.
      example: 11111112cMQwSC9qirWGjZM6gLGwW69X22mqwLLGP
    DataSlice:
      type: object
      required:
        - offset
        - length
      properties:
        length:
          type: integer
          minimum: 0
        offset:
          type: integer
          minimum: 0
    FilterSelector:
      type: object
      properties:
        memcmp:
          $ref: '#/components/schemas/Memcmp'
    Limit:
      type: integer
      format: uint64
      minimum: 0
    SerializablePubkey:
      type: string
      description: A Solana public key represented as a base58 string.
      default: 111111131h1vYVSYuKP6AhS86fbRdMw9XHiZAvAaj
      example: 111111131h1vYVSYuKP6AhS86fbRdMw9XHiZAvAaj
    Context:
      type: object
      required:
        - slot
      properties:
        slot:
          type: integer
          format: uint64
          default: 100
          example: 100
    PaginatedAccountList:
      type: object
      required:
        - items
      properties:
        cursor:
          $ref: '#/components/schemas/Hash'
        items:
          type: array
          items:
            $ref: '#/components/schemas/Account'
      additionalProperties: false
    Memcmp:
      type: object
      required:
        - offset
        - bytes
      properties:
        bytes:
          $ref: '#/components/schemas/Base58String'
        offset:
          type: integer
          minimum: 0
    Account:
      type: object
      required:
        - hash
        - owner
        - lamports
        - tree
        - leafIndex
        - slotCreated
      properties:
        address:
          $ref: '#/components/schemas/SerializablePubkey'
        data:
          $ref: '#/components/schemas/AccountData'
        hash:
          $ref: '#/components/schemas/Hash'
        lamports:
          $ref: '#/components/schemas/UnsignedInteger'
        leafIndex:
          $ref: '#/components/schemas/UnsignedInteger'
        owner:
          $ref: '#/components/schemas/SerializablePubkey'
        seq:
          $ref: '#/components/schemas/UnsignedInteger'
        slotCreated:
          $ref: '#/components/schemas/UnsignedInteger'
        tree:
          $ref: '#/components/schemas/SerializablePubkey'
      additionalProperties: false
    Base58String:
      type: string
      description: A base 58 encoded string.
      default: 3J98t1WpEZ73CNm
      example: 3J98t1WpEZ73CNm
    AccountData:
      type: object
      required:
        - discriminator
        - data
        - dataHash
      properties:
        data:
          $ref: '#/components/schemas/Base64String'
        dataHash:
          $ref: '#/components/schemas/Hash'
        discriminator:
          $ref: '#/components/schemas/UnsignedInteger'
      additionalProperties: false
    UnsignedInteger:
      type: integer
      format: uint64
      default: 100
      example: 100
    Base64String:
      type: string
      description: A base 64 encoded string.
      default: SGVsbG8sIFdvcmxkIQ==
      example: SGVsbG8sIFdvcmxkIQ==

````