# Error codes and status codes
Source: https://cobo.com/developers/v2/api-references/error-codes

List of error codes for the WaaS 2.0 API, with explanations and troubleshooting tips.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This article explains the common error codes and HTTP status codes you may encounter when using the Cobo WaaS 2.0 API and how to resolve the errors.

### Error codes

#### General errors

| Error code | Description                                                                                                                          | Solution                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                             |
| ---------- | ------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 1000       | Internal Server Error. This error can be caused by several issues including expired [Org Access Tokens](/developers/v2/apps/org-access-tokens). | Check your server configuration settings, including whether your Org Access Token has expired, and try again later.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| 1003, 2003 | One or more required parameters are missing in the request.                                                                          | The `error_message` field names the specific missing parameter. Identify that parameter, confirm which parameters are required in the API reference for the operation you are calling, add it, and retry.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| 1006, 2006 | One or more parameters are in an invalid format or contain unsupported values.                                                       | The `error_message` field names the parameter that failed validation. Check the API reference for the operation you are calling to confirm the expected type, format, and allowed values for that parameter, then correct the value and retry.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       |
| 2000       | Internal error occurred during processing.                                                                                           | This is a temporary error on Cobo's side. Retry after a short delay. If the error persists, contact Cobo support at [help@cobo.com](mailto:help@cobo.com) and provide the `error_id` from the response so the failure can be traced.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 |
| 2021       | The requested API endpoint is not implemented or is currently unavailable.                                                           | Confirm the request path and HTTP method exactly match the operation in the API reference (a trailing slash or wrong method also returns this error). If they are correct, the endpoint may be temporarily unavailable — retry after a short delay using exponential backoff.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        |
| 2024       | API key authentication failed.                                                                                                       | <ul><li>If `error_message` is `Your API key is not registered in this environment...`: you are using a key registered in the wrong environment. Switch to the correct API host and use the matching API key. See [Environments](/developers/v2/guides/overview/environments).</li><li>If `error_message` is `Your API key is not yet activated...` or `Api key is not activated`: complete Admin approval in Cobo Guard for the key to become Active.</li><li>If `error_message` mentions the IP whitelist: add your server's egress IP to the key's allowlist in Cobo Portal.</li><li>For signature failures, ensure the canonical string follows the format `METHOD\|PATH\|NONCE\|PARAMS\|BODY` with the nonce identical to the `Biz-Api-Nonce` header. See [Authentication](/developers/v2/guides/overview/cobo-auth).</li></ul>For details, see <a href="https://manuals.cobo.com/en/portal/developer-console/create-api-key">Register an API Key</a>.                                                                                                                                                                                                                                                                                                                                                                                                 |
| 2025, 4001 | Forbidden access to the requested resource.                                                                                          | <ul><li>Check the permissions, wallet scopes, and resource scopes associated with your API key. You can refer to [Permissions and wallet scopes](/developers/v2/guides/overview/permissions-and-scopes) for details.</li><li>If the error is related to user roles (for example, creating withdrawals or initiating transactions), make sure the operator has the required role (for example, withdrawals typically require Spender or Admin).</li><li>If the error message contains "Resource out of organization (4001)", it usually means the resource you are accessing (for example, `wallet_id`) belongs to a different organization than the API key.</li><li>If you have granted permissions but still get forbidden, check whether you are mixing Dev/Prod API keys or calling the wrong environment domain.</li><li>For Custodial Wallet operations, verify that the permission is granted at the correct (upper) scope level (some permissions must be enabled in the parent Custodial Wallet settings).</li><li>If this operation requires an enabled capability (feature flag / allowlist), ensure it is enabled in the target environment.</li><li>If this is chain/asset related (for example, adding a chain but still seeing forbidden), confirm the chain/capability is enabled in your pricing plan/configuration.</li></ul> |
| 2026       | Too many requests.                                                                                                                   | Reduce your request frequency and retry after a short delay. For polling or batch patterns, implement exponential backoff — for example, start with a 1-second delay and double it on each retry (1s, 2s, 4s, ...) up to a maximum.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| 2028       | The requested resource was not found.                                                                                                | The resource ID does not exist in your organization or was created in a different environment. List the relevant resources to confirm the correct ID (for example, call [List transactions](/developers/v2/api-references/transactions/list-transactions) for a `transaction_id`), then retry with a valid ID. Confirm you are calling the same environment (Development or Production) in which the resource was created.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 2029       | The value provided for the `status` parameter is not one of the allowed values.                                                      | The allowed values for `status` depend on the operation (for example, transaction status differs from screening status). In the API reference, open the operation you are calling and provide one of the `status` enum values listed for its request parameters.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     |
| 10000      | This organization has read-only permissions in Cobo Portal.                                                                          | Your organization currently has read-only access, so write operations are rejected. A team admin must log in to Cobo Portal and review the organization's access status in the organization settings; only a team admin can change the access level. Members without the admin role cannot change this setting.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |

#### Pricing plan errors

| Error code | Description                                                                                                 | Solution                                                                                                                                                                                                                                                     |
| ---------- | ----------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 2050       | No pricing plan is active for this organization, so billable API operations are blocked.                    | Activate a pricing plan: log in to Cobo Portal, open **Bills & Payments**, and select a plan. For more information, see [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction).                              |
| 2051       | The organization's pricing plan has expired, so billable operations are blocked until it is renewed.        | Renew your pricing plan: in Cobo Portal, open **Bills & Payments** and renew or select a plan. For more information, see [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction).                             |
| 2052       | The organization has exceeded the usage quota included in its current pricing plan.                         | Wait for the next billing cycle to reset the quota, or upgrade to a higher plan in Cobo Portal under **Bills & Payments**. For more information, see [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction). |
| 2053       | The current pricing plan does not include the entitlement required for this operation.                      | Upgrade to a plan that includes this feature in Cobo Portal under **Bills & Payments**. For more information, see [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction).                                    |
| 2054       | Payment for the current pricing plan is overdue (the organization is in arrears), so the plan is suspended. | Settle the outstanding balance in Cobo Portal under **Bills & Payments** to restore service. For more information, see [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction).                               |

#### Wallet configuration errors

| Error code | Description                                                                                                                                                                                                  | Solution                                                                                                                                                                                                                                                                                                                                                                  |
| ---------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 2101       | The wallet name exceeds the maximum allowed character length.                                                                                                                                                | Wallet names can contain up to 100 characters. The `error_message` reports the exact limit that applies to your request. Shorten the wallet name to that limit or fewer, then retry.                                                                                                                                                                                      |
| 2102       | The wallet name contains invalid characters.                                                                                                                                                                 | The Cobo API rejects wallet names that contain any of the following characters: `+`, `-`, `=`, `@`. Remove these characters from the wallet name and retry.                                                                                                                                                                                                               |
| 2103       | A wallet with this name already exists in the organization.                                                                                                                                                  | Wallet names must be unique within an organization. Choose a name that is not already used by another wallet and retry. To see names in use, list your existing wallets.                                                                                                                                                                                                  |
| 2104       | The specified chain is not enabled for this organization's pricing plan.                                                                                                                                     | To check which chains are already enabled, call the [List enabled chains](/developers/v2/api-references/wallets/list-enabled-chains) operation. If you need to enable or disable chains in Cobo Portal, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains). Then retry with a chain that is enabled for your organization.                  |
| 2105       | For UTXO-based tokens (such as BTC), all available UTXOs are currently locked by a pending transaction or a transaction pending KYT screening. A new transfer cannot proceed until those UTXOs are released. | Call the [List transactions](/developers/v2/api-references/transactions/list-transactions) operation, filtered to this wallet, to find the pending transactions that are holding the UTXOs. The UTXOs are released only when those transactions reach a terminal state (for example, completed or failed). Retry the transfer after the locking transactions reach a terminal state. |

#### Transfer errors

The following error codes are returned by transfer and withdrawal operations.

| Error code   | Description                                                                                                                                                                                                           | Solution                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| ------------ | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 30000        | Unauthorized. You do not have permission to perform this transfer.                                                                                                                                                    | Check the permissions and wallet scopes associated with your API key. See [Permissions and wallet scopes](/developers/v2/guides/overview/permissions-and-scopes) for details.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        |
| 30001, 12009 | The `request_id` has already been used.                                                                                                                                                                               | Use a unique `request_id` for each new transaction. Duplicate `request_id` values are rejected to prevent duplicate transactions.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| 30002        | The specified token is not supported for this operation or organization.                                                                                                                                              | Verify the `token_id` is correct. Call the [List supported tokens](/developers/v2/api-references/wallets/list-supported-tokens) operation to get the full list of supported tokens.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| 30003        | The wallet type does not support this transfer operation.                                                                                                                                                             | Verify that the wallet type is compatible with the requested transfer.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    |
| 30004        | The source wallet ID is invalid or the wallet does not exist.                                                                                                                                                         | Verify the `from_wallet_id` value is correct and the wallet belongs to your organization.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 |
| 30005        | The source address format is invalid or not compatible with the token.                                                                                                                                                | Provide a valid source address that is compatible with the token type.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    |
| 30006        | The source address encoding format is not supported.                                                                                                                                                                  | Use an address encoding format that is supported for this token.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                          |
| 30007        | Invalid amount. The value is not a valid number or does not meet the required format or range.                                                                                                                        | Provide a positive numeric amount. Call the [Get token information](/developers/v2/api-references/wallets/get-token-information) operation to retrieve the token's `decimal` precision and ensure the amount does not exceed it.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     |
| 30008        | The `abs_amount` value must be greater than 0.                                                                                                                                                                        | Provide a positive, non-zero value for `abs_amount`.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 30009        | The amount cannot be less than zero.                                                                                                                                                                                  | Provide a non-negative amount.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| 30010        | The withdrawal amount is below the minimum threshold for this token and cannot be processed.                                                                                                                          | Increase the withdrawal amount. Call the [Get token information](/developers/v2/api-references/wallets/get-token-information) operation to retrieve the `dust_threshold` value for this token.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       |
| 30011        | The deposit amount is below the minimum deposit threshold for this token.                                                                                                                                             | Increase the deposit amount. Call the [Get token information](/developers/v2/api-references/wallets/get-token-information) operation to retrieve the `minimum_deposit_threshold` value for this token.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                               |
| 30012, 12007 | The transfer amount exceeds the wallet's available balance.                                                                                                                                                           | Check the wallet's available balance, which equals the total balance minus any pending and reserved amounts. Call the [Get wallet balance](/developers/v2/api-references/wallets/get-wallet-balance) operation to verify.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| 30013        | The fee token balance is insufficient to cover the transaction fee.                                                                                                                                                   | Ensure the wallet or Fee Station has sufficient balance in the fee token (for example, ETH on EVM chains) to cover the transaction fee.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   |
| 30014        | The destination address is invalid or not compatible with the token.                                                                                                                                                  | Provide a valid destination address that is compatible with the token type.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                               |
| 30015        | The destination wallet ID is invalid or the wallet does not exist.                                                                                                                                                    | Verify the `to_wallet_id` value is correct and the wallet belongs to your organization.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   |
| 30016        | The number of transaction categories exceeds the maximum of 5.                                                                                                                                                        | Reduce the number of categories in the `category_names` field to 5 or fewer.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| 30017        | The category name exceeds the maximum of 30 characters.                                                                                                                                                               | Shorten the category name to 30 characters or fewer.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 30018        | The description exceeds the maximum of 100 characters.                                                                                                                                                                | Shorten the `description` field to 100 characters or fewer.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                               |
| 30022        | An invalid trading account type was specified as the transfer source for an Exchange Wallet.                                                                                                                          | Provide a valid trading account type as the transfer source.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| 30023        | An invalid trading account type was specified as the transfer destination for an Exchange Wallet.                                                                                                                     | Provide a valid trading account type as the transfer destination.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| 30024        | Neither `to_wallet_id` nor `to_address` was provided.                                                                                                                                                                 | Provide either `to_wallet_id` or `to_address` as the transfer destination.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                |
| 30025        | Withdrawals are currently unavailable for this wallet or token.                                                                                                                                                       | In Cobo Portal, open the target wallet, locate the target token in the wallet's token or asset list, and check whether that token row provides a **Withdraw** action. If **Withdraw** is not available, that wallet/token combination does not support withdrawals. If the token is not shown in the list, add the token to the wallet first; if the add-token flow indicates that the token's chain is not enabled, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains).                                                                                                                                                                                                                         |
| 30026        | Transfers are currently unavailable for this wallet.                                                                                                                                                                  | In Cobo Portal, open **Wallets** > the wallet type that matches this request > the target wallet, then verify from the wallet detail page that transfers are allowed for that wallet. If the wallet is restricted by wallet status, approval settings, or policy configuration, update the relevant setting before retrying.                                                                                                                                                                                                                                                                                                                                                                                                              |
| 30027        | Deposits into the destination wallet are currently unavailable.                                                                                                                                                       | Confirm that the destination token has been added to the destination wallet and that the token's chain is enabled for your organization. If you need to enable or disable chains in Cobo Portal, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains). If that token or wallet still does not support deposits, choose a destination wallet that supports deposits.                                                                                                                                                                                                                                                                                                                                |
| 30028        | The `request_id` parameter is missing or invalid.                                                                                                                                                                     | Provide a valid, non-empty `request_id` with the request.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 |
| 30029        | Trading account sub-wallets cannot initiate withdrawal transactions in an Exchange Wallet.                                                                                                                            | Use the Exchange Wallet's main account to initiate the withdrawal, not a trading account sub-wallet.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 30030        | The deposit or withdrawal operation cannot proceed because Cobo has temporarily suspended deposit or withdrawal processing for this token. The platform rejects the related operation until the suspension is lifted. | You cannot lift this suspension yourself; it is controlled on Cobo's side. To be notified when a token is suspended, subscribe to the `token.suspended.deposit` and `token.suspended.withdraw` events when you register a webhook endpoint, either on Cobo Portal (see [Register a webhook endpoint](https://manuals.cobo.com/en/portal/developer-console/webhooks-create), where you select the event types to subscribe to) or by calling the [Register webhook endpoint](/developers/v2/api-references/developers--webhooks/register-webhook-endpoint) operation (`POST /webhooks/endpoints`) with `subscribed_events` set to `["token.suspended.deposit", "token.suspended.withdraw"]`. Then retry the operation after the suspension is lifted. |
| 30031        | The specified token has not been enabled for this organization.                                                                                                                                                       | Call the [List enabled tokens](/developers/v2/api-references/wallets/list-enabled-tokens) operation to confirm the token is not yet enabled. Then add the token to the target wallet; if the flow indicates that the token's chain is not yet enabled, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains). Retry after the token is available in the wallet.                                                                                                                                                                                                                                                                                                                                                |
| 30032        | No key share holder group is available for signing in this MPC Wallet.                                                                                                                                                | In Cobo Portal, go to **Wallets** > **MPC Wallets** > the target vault > **Key Share Management**. Confirm that the vault has an available **Main Group** or **Signing Group** that can sign this transaction. If neither exists or the available group is unusable, create or recover the required group in **Key Share Management** first, then retry the transaction.                                                                                                                                                                                                                                                                                                                                                                  |
| 30033        | The recipient address does not belong to Cobo, or Cobo Loop has been disabled for these wallets.                                                                                                                      | Verify that the recipient address is a Cobo address and that Cobo Loop is enabled for both wallets. To send to a non-Cobo address, use a standard withdrawal instead.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     |
| 30035        | The Exchange Wallet is connected in Observation mode, which is read-only and does not support withdrawals.                                                                                                            | Switch to an Exchange Wallet connected in Normal mode, or use a different wallet that has withdrawal permissions.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| 30036        | The Fee Station balance is insufficient. Transactions cannot proceed until it is recharged.                                                                                                                           | In Cobo Portal, go to **Fee Station**. You can use the **USD / USD Stablecoins** tab to deposit supported USD stablecoins, or switch to the **Gas Token** tab to deposit the native gas token required by the target network. Retry after the balance is updated.                                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| 30037        | The source and destination wallets are not eligible for Cobo Loop transactions.                                                                                                                                       | Verify that both wallets support Cobo Loop. Use a standard transfer for wallets that are not Cobo Loop eligible.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                          |
| 30038        | The Fee Station token balance is insufficient to cover the transaction fee.                                                                                                                                           | In Cobo Portal, go to **Fee Station** > **Gas Token** and deposit the exact native gas token required by the network for this transaction. Retry after that token balance is sufficient.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| 30039        | Cobo's Fee Station balance is insufficient to pay for gas.                                                                                                                                                            | This error is caused by a temporary condition on Cobo's side. Retry after a short delay.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |

#### Token and balance errors

| Error code | Description                                                                      | Solution                                                                                                                                                                                                   |
| ---------- | -------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 12002      | The specified token is not supported by Cobo.                                    | Choose a supported token. Call the [List supported tokens](/developers/v2/api-references/wallets/list-supported-tokens) operation to get the full list of supported tokens.                                           |
| 12025      | The UTXOs specified in `included_utxos` or `excluded_utxos` are invalid.         | Verify the UTXOs specified in `included_utxos` or `excluded_utxos`.                                                                                                                                        |
| 60010      | The specified token has not been enabled for this organization.                  | Enable the token for your organization in Cobo Portal. Call the [List enabled tokens](/developers/v2/api-references/wallets/list-enabled-tokens) operation to see all tokens currently enabled for your organization. |
| 60020      | The specified address is not enabled for the given token and wallet combination. | Verify that the address is associated with the correct wallet and token in your organization settings.                                                                                                     |

#### Transaction management errors

| Error code | Description                                                                                   | Solution                                                                                                                                                                                                                                                                                                                 |
| ---------- | --------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 60001      | The specified organization was not found.                                                     | Verify that your API key belongs to the correct organization and that you are calling the correct environment.                                                                                                                                                                                                           |
| 60002      | The transaction type is invalid.                                                              | Provide one of the supported transaction types: `Transfer`, `ContractCall`, or `MessageSign`.                                                                                                                                                                                                                            |
| 60003      | The transaction fee could not be estimated.                                                   | Retry the fee estimation after a short delay. If the error persists, verify that the token is supported and that the chain is enabled for your organization. If you need to review or change enabled chains in Cobo Portal, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains). |
| 60004      | The transaction could not be found for the requested action.                                  | Verify the `transaction_id` value and confirm that the transaction exists in your organization.                                                                                                                                                                                                                          |
| 60005      | The transaction cannot be canceled because it is in a state that does not allow cancellation. | Check the current transaction status. Only transactions in certain states (such as `Pending`) can be canceled.                                                                                                                                                                                                           |
| 60006      | The transaction cannot be dropped.                                                            | The transaction is in a state that does not allow it to be dropped. Check the transaction status before retrying.                                                                                                                                                                                                        |
| 60007      | The transaction cannot be sped up.                                                            | The transaction is in a state that does not allow a speed-up. This may occur when the transaction is already confirmed or in a terminal state.                                                                                                                                                                           |

#### MPC wallet errors

| Error code | Description                                                          | Solution                                                                                                                                                                                                                                                                            |
| ---------- | -------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 50000      | The MPC Vault does not have backed-up key shares for the Main Group. | In Cobo Portal, go to **Wallets** > **MPC Wallets** > the target vault > **Key Share Management**. Open the **Main Group**, check its backup status, and complete the pending key share backup for every holder. Retry this operation only after the Main Group shows as backed up. |

#### Smart contract and EVM errors

The following error codes are returned by EVM contract call operations.

**Note:** Error codes 40001–40003 are also returned by transaction category operations with different meanings. Use the operation you called and the `error_message` to determine which meaning applies.

| Error code | Description                                                                      | Solution                                                                                                                                                                                                 |
| ---------- | -------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 5001       | The contract ABI is invalid or cannot be parsed.                                 | Verify that the ABI JSON is correctly formatted and complete.                                                                                                                                            |
| 5002       | One or more parameters passed to the EVM operation are invalid.                  | Check the parameter types and values against the contract ABI definition.                                                                                                                                |
| 5003       | The transaction calldata is invalid or improperly encoded.                       | Verify that the calldata is correctly ABI-encoded for the target function.                                                                                                                               |
| 5004       | The requested EVM resource was not found.                                        | Check the contract address and chain ID in the request.                                                                                                                                                  |
| 40001      | The external data source (such as a block explorer) rate limit has been reached. | Retry after a short delay. This is a temporary condition caused by upstream rate limits.                                                                                                                 |
| 40002      | The contract source code is not verified on the block explorer.                  | Verify the contract source code on the relevant block explorer (such as Etherscan) before attempting ABI-related operations.                                                                             |
| 40003      | The specified chain is not supported for this EVM operation.                     | Use a supported chain. If you need to review which chains are enabled for your organization in Cobo Portal, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains). |

#### MFA errors

The following error codes are returned when Cobo Guard multi-factor authentication (MFA) is required or fails.

| Error code | Description                                                                               | Solution                                                                                                                                                                                                                                                                                                                                                         |
| ---------- | ----------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 40201      | The Cobo Guard key provided is invalid or has expired.                                    | In Cobo Portal, click your avatar in the top-right corner, then go to **Account** > **Security**. In the **Cobo Guard** section, either click **View Pubkey and TSS Node ID** to confirm you are using the correct active key, or click **Reset** / **Set Up** to bind a new Cobo Guard key. After the active key is updated, retry the operation with that key. |
| 40202      | The Cobo Guard request is still pending and has not been completed.                       | Wait for the Guard request to be approved or rejected before proceeding.                                                                                                                                                                                                                                                                                         |
| 40203      | The Cobo Guard request has no approval or rejection result yet.                           | Check the status of the pending Guard request and complete it before retrying.                                                                                                                                                                                                                                                                                   |
| 40204      | The user performing this operation must be the same user who initiated the Guard request. | Ensure the same user account is used for both initiating and completing the Cobo Guard MFA request.                                                                                                                                                                                                                                                              |

#### Transaction category errors

The following error codes are returned by transaction category management operations.

**Note:** Error codes 40001–40003 are also returned by EVM operations with different meanings. Use the operation you called and the `error_message` to determine which meaning applies.

| Error code | Description                                                         | Solution                                             |
| ---------- | ------------------------------------------------------------------- | ---------------------------------------------------- |
| 40000      | The category name exceeds 30 characters.                            | Shorten the category name to 30 characters or fewer. |
| 40001      | The specified organization was not found.                           | Verify your organization ID and API key environment. |
| 40002      | The number of transaction categories has reached the maximum limit. | Delete unused categories before creating new ones.   |
| 40003      | A category with this name already exists in the organization.       | Use a unique category name.                          |
| 40004      | The category name contains invalid characters.                      | Use only allowed characters in the category name.    |

#### Compliance and KYT errors

The following error codes are returned by compliance and Know Your Transaction (KYT) operations.

| Error code | Description                                                                                                                                    | Solution                                                                                                                                                                                                                                                                                                                                                           |
| ---------- | ---------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 40101      | The compliance request for the specified `transaction_id` was not found.                                                                       | Verify the `transaction_id` is correct and that a compliance check has been initiated for it.                                                                                                                                                                                                                                                                      |
| 40102      | The compliance request cannot be retried because it is not in a failed state.                                                                  | Check the current status of the compliance request before retrying. Only requests in a `Failed` state can be retried.                                                                                                                                                                                                                                              |
| 40103      | This transaction does not support the requested operation (it is not an EOA/Web3 transaction, or it does not have an on-chain transaction ID). | Confirm that the request type you are submitting is supported by the compliance API.                                                                                                                                                                                                                                                                               |
| 40104      | The KYT disposal type provided is invalid.                                                                                                     | Provide a valid disposal type for the KYT operation.                                                                                                                                                                                                                                                                                                               |
| 40105      | The specified KYT request was not found.                                                                                                       | Verify the KYT request ID.                                                                                                                                                                                                                                                                                                                                         |
| 40106      | A disposal request for this KYT screening already exists.                                                                                      | Check for an existing disposal request before creating a new one.                                                                                                                                                                                                                                                                                                  |
| 40107      | A withdrawal request for this KYT disposal already exists.                                                                                     | Check for an existing withdrawal request before creating a new one.                                                                                                                                                                                                                                                                                                |
| 40108      | The `status` filter value provided when querying the KYT audit list is invalid.                                                                | Use a `status` value supported by that operation when querying the KYT audit list.                                                                                                                                                                                                                                                                                 |
| 40109      | No KYT screening request was found for the specified `transaction_id`.                                                                         | Verify the `transaction_id` and ensure that a KYT screening was initiated for it.                                                                                                                                                                                                                                                                                  |
| 40110      | No KYT screening request was found for the specified `screening_request_id`.                                                                   | Verify the `screening_request_id` value.                                                                                                                                                                                                                                                                                                                           |
| 40111      | The transaction's current status does not allow a disposal action.                                                                             | Check the transaction's current status before initiating a disposal.                                                                                                                                                                                                                                                                                               |
| 40112      | The disposal parameters provided are invalid for this transaction.                                                                             | Review the disposal parameters and ensure they are consistent with the transaction's screening result.                                                                                                                                                                                                                                                             |
| 40113      | The KYT request is already being disposed of or has already been disposed of, so a new disposal action cannot be initiated.                    | Do not submit a duplicate disposal request for the same KYT request. Confirm the request's current disposal status first, then decide whether any further action is needed.                                                                                                                                                                                        |
| 40114      | The transaction's current status does not allow an unfreeze action.                                                                            | Check the transaction's current status before attempting to unfreeze it.                                                                                                                                                                                                                                                                                           |
| 40115      | The disposal fee for the KYT request is invalid.                                                                                               | Provide both `estimated_fee_type` and `estimated_fee_detail` in the KYT disposal request. This error occurs when `estimated_fee_type` is empty, or when `estimated_fee_detail` is empty or cannot be parsed into a valid transaction fee object. Check the API reference for the disposal operation for the expected `estimated_fee_detail` structure, then retry. |
| 40116      | The disposal fee for the screening request is invalid.                                                                                         | Provide a non-empty `estimate_transaction_fee` value in the screening disposal request. This error occurs when that field is missing or empty.                                                                                                                                                                                                                     |
| 40117      | The fee payment method for the KYT disposal is invalid.                                                                                        | Set `fee_payment_method` to one of the allowed values: `CUSTOMER_FEE_STATION`, `CUSTOMER_CURRENT_ADDRESS`, or `COBO_FEE_STATION`. An empty or missing value is also rejected.                                                                                                                                                                                      |
| 40118      | The destination address for the KYT disposal is invalid.                                                                                       | The `to_address` must be either one of the original sender addresses of the screened transaction or a valid address on that transaction's chain. Provide an address that meets one of these conditions and retry.                                                                                                                                                  |
| 40119      | An error occurred during the KYT disposal process.                                                                                             | Verify your request parameters are correct, then retry. If the error persists, go to **Approvals** > **Initiated By Me** or **All Approvals** in Cobo Portal, open the KYT disposal approval record for this request, and review its latest status and failure details before resubmitting.                                                                        |
| 40120      | The disposal amount for the screening request is invalid.                                                                                      | Verify the disposal amount in the screening disposal request.                                                                                                                                                                                                                                                                                                      |
| 40121      | The disposal amount for the KYT request is invalid.                                                                                            | Verify the disposal amount in the KYT disposal request.                                                                                                                                                                                                                                                                                                            |
| 40122      | The wallet balance is insufficient to cover the estimated transaction fee for the disposal.                                                    | In Cobo Portal, open **Wallets** > the wallet type that holds the screened funds > the target wallet, and confirm that the wallet holds enough native gas token to pay the disposal fee. If your disposal uses Fee Station, also go to **Fee Station** and confirm the fee-paying token balance is sufficient there before retrying.                               |
| 40123      | A disposal action cannot be initiated because the transaction is not currently frozen.                                                         | A KYT disposal can only be applied to frozen transactions. Verify the transaction's current status before proceeding.                                                                                                                                                                                                                                              |
| 40124      | No compliance request was found for the specified transaction hash.                                                                            | Verify the transaction hash.                                                                                                                                                                                                                                                                                                                                       |
| 40125      | The app check request for the specified `transaction_id` was not found.                                                                        | Verify the `transaction_id` and ensure that a compliance app check was initiated for it.                                                                                                                                                                                                                                                                           |
| 40126      | The KYT screening completion result is invalid or malformed.                                                                                   | Review the result format returned by the KYT provider.                                                                                                                                                                                                                                                                                                             |

#### Travel Rule errors

The following error codes are returned by Travel Rule compliance operations.

| Error code | Description                                                                        | Solution                                                                                                        |
| ---------- | ---------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------- |
| 70001      | A general Travel Rule error occurred.                                              | Check the error message for details and review your Travel Rule request parameters.                             |
| 70002      | The originator KYC information is invalid or incomplete.                           | Provide complete and valid KYC information for the originator.                                                  |
| 70003      | The Travel Rule vendor code is invalid.                                            | Provide a valid vendor code.                                                                                    |
| 70004      | The originator's natural person entity information is missing or incomplete.       | Complete all required natural person entity fields for the originator.                                          |
| 70005      | The originator's legal entity information is missing or incomplete.                | Complete all required legal entity fields for the originator.                                                   |
| 70006      | The originator information is missing or incomplete.                               | Provide all required originator information.                                                                    |
| 70007      | An error occurred while entering the sender information.                           | Check the error message for details and verify the sender information fields.                                   |
| 70008      | This Travel Rule operation is not supported for self-custody wallets.              | Use a Cobo-managed wallet for this Travel Rule operation.                                                       |
| 70009      | Originator information has already been submitted for this record.                 | Originator information can only be submitted once per record. Review the existing record if updates are needed. |
| 70010      | The self-custody wallet signature verification failed.                             | Ensure the signature is generated correctly for the self-custody wallet address.                                |
| 70011      | The legal entity information is incomplete — required fields are missing.          | Provide all required fields for the legal entity.                                                               |
| 70012      | The natural person entity information is incomplete — required fields are missing. | Provide all required fields for the natural person entity.                                                      |
| 70013      | This address has already been verified.                                            | No further action is needed. Address verification is a one-time operation.                                      |

### HTTP status codes

| Status code | Description                                                                                                                          | Solution                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                           |
| ----------- | ------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 200         | OK.                                                                                                                                  | N/A                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                |
| 400         | Bad request.                                                                                                                         | Check the request parameters.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 401         | Unauthorized.                                                                                                                        | Check whether the API key matches the current environment (Dev/Prod), whether the API signature is correct, and whether the `timestamp` is valid and consistent with the fields used in signing.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   |
| 403         | Forbidden.                                                                                                                           | <ul><li>Check the business error code in the response body first (for example, `2025`/`4001`) and troubleshoot permissions, roles, scopes, and organization ownership accordingly.</li><li>If you access the API via a reverse proxy or gateway, check gateway policies, egress public IP, WAF/firewall rules, and whether headers or paths are blocked or rewritten (for example, Cloudflare or Nginx).</li><li>If the failure is permission-related, review the operator's role in **Organization Settings** > **User Roles** and review the API key's configuration in **Developers** > **Custody Developers** > **API Keys**.</li><li>If the operation is blocked by transaction governance, go to **Wallets** > **Transaction Policies** and confirm the relevant policy allows this API operation.</li></ul> |
| 404         | Not Found.                                                                                                                           | Check the requestURL.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| 405         | Method Not Allowed.                                                                                                                  | Use a supported HTTP method.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       |
| 406         | Not Acceptable.                                                                                                                      | Ensure the request content format is JSON.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| 429         | Too Many Requests.                                                                                                                   | Reduce request frequency and try again later.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 500         | Internal Server Error. This error can be caused by several issues including expired [Org Access Tokens](/developers/v2/apps/org-access-tokens). | Check your server configuration settings, including whether your Org Access Token has expired, and try again later.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                |
| 502         | Bad Gateway.                                                                                                                         | Check the connectivity and try again later.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        |
| 503         | Service Unavailable.                                                                                                                 | Try again later.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   |


# Pagination
Source: https://cobo.com/developers/v2/api-references/pagination

Guide to implementing pagination in WaaS 2.0 API, including parameters and best practices.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Pagination in the WaaS 2.0 API allows you to retrieve data in manageable chunks. You can control the page size and navigate through the dataset using three query parameters:

* `limit`: This parameter defines the maximum number of objects you want to receive in each response.

* `before`: A cursor indicating the position before the current page. This value is generated by Cobo and returned in the response. If you are paginating forward from the beginning, you do not need to provide it on the first request. When paginating backward (to the previous page), you should pass the before value returned from the last response.

  Suppose the current data is ordered as Object A, Object B, and Object C.  If you set `before` to the ID of Object C (`RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk`), the response will include Object B and Object A.

* `after`: A cursor indicating the position after the current page. This value is generated by Cobo and returned in the response. You do not need to provide it on the first request. When paginating forward (to the next page), you should pass the after value returned from the last response.

  Suppose the current data is ordered as Object A, Object B, and Object C. If you set `after` to the ID of Object A (`RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk`), the response will include Object B and Object C.

**Notes**:

* If you set both `after` and `before`, an error will occur.
* If you leave both `before` and `after` empty, the first page of data is returned.
* If you set `before` to `infinity`, the last page of data is returned.


# Send a request with API Playground
Source: https://cobo.com/developers/v2/api-references/playground

Interactive API playground for the WaaS 2.0 API, allowing developers to test endpoints and view responses.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

The API Playground is a web-based tool designed for developers looking to explore and experiment with the Cobo WaaS 2.0 API directly from the Developer Hub, all within the browser.

## Prerequisites

Before using the API Playground, make sure you have completed the following:

* Set up your Cobo Account and create the required API key and API secret. For instructions, see [Set up Cobo Accounts](https://manuals.cobo.com/en/accounts/sign-up) and [Generate an API key and an API secret](/developers/v2/guides/overview/cobo-auth#generate-an-api-key-and-an-api-secret).
* Register the API key on Cobo Portal based on the environment that you use. For more details, refer to [Register the API key](/developers/v2/guides/overview/cobo-auth#register-the-api-key) and [Environments](/developers/v2/guides/overview/environments).

## Steps

1. Go to any API operation in the API Reference and click **Try it**.

   <img alt="API Playground try" />

   The API Playground panel will appear, showing a request editor, sample codes for different programming languages, and a response viewer.

   <img alt="API Playground panel" />

2. Modify the request as follows:

   * In the **Authorization** section, enter your API secret into the `BIZ-API-KEY` field.
     <Note>For API requests sent via the API Playground, you only need to provide your API secret in the request headers. However, for actual API requests, you need to provide your API key, a nonce, and an API signature as request headers. For more details, see [Authentication](/developers/v2/guides/overview/cobo-auth). </Note>
   * Set the path parameters, query parameters, and request body as needed.

3. Choose the API base URL that you want to send requests to:

   * Development environment: [https://api.dev.cobo.com/v2/](https://api.dev.cobo.com/v2/)
   * Production environment: [https://api.cobo.com/v2/](https://api.cobo.com/v2/)

   You can switch between development and production directly in the API Playground by clicking the arrow icon next to the base URL.

   <img alt="API Playground switch environment" />

   <Note> For security reasons, it is strongly recommended to use the development environment for testing purposes. For more information about differences between the development and production environments, see [Environments](/developers/v2/guides/overview/environments).</Note>

4. Click the **Send** button to submit the request.

Upon successful submission, you will find the response returned from the WaaS service in the response viewer.


# Use Postman to call the Wallet-as-a-Service (WaaS) 2.0 API
Source: https://cobo.com/developers/v2/api-references/use-postman-to-call-waas-api

Guide to using Postman for calling the WaaS 2.0 API.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## **Overview**

This guide introduces how to use Postman to call the Wallet-as-a-Service (WaaS) 2.0 API.

## **Prerequisites**

* A Postman account.
* Follow the instructions in [Set up your account and organization](https://manuals.cobo.com/en/portal/quick-start-guide) to set up your Cobo account and create your organization. If an organization has already been set up, ask your organization admin to invite you to join the organization.
  Note: This guide uses the development environment in all of its examples. Please create your organization in the development environment at [https://portal.dev.cobo.com/](https://portal.dev.cobo.com/).
* You have [generated an API key and an API secret](/developers/v2/guides/overview/cobo-auth#generate-an-api-key-and-an-api-secret) and [registered the API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key) on Cobo Portal.

## Create a collection

1. Download the WaaS 2.0 API specification from [GitHub](https://github.com/CoboGlobal/developer-site/blob/master/v2/cobo_waas2_openapi_spec/dev_openapi.yaml).
2. Visit [https://www.postman.com/](https://www.postman.com/) or launch Postman on your local machine.
3. [Create a new workspace](https://learning.postman.com/docs/collaborating-in-postman/using-workspaces/create-workspaces/#create-a-new-workspace) if you do not have one yet.
4. Import the API specification you have just downloaded into the workspace. To learn how to import a specification file, see [Import an API into Postman](https://learning.postman.com/docs/designing-and-developing-your-api/importing-an-api/)

## Add a pre-request script

Use [pre-request-script.js](https://github.com/CoboGlobal/cobo-waas2-js-sdk/blob/master/src/PreRequestScript.js) as the pre-request script of your collection. This script automatically calculates the authentication-related parameter values and adds them as your request headers. To learn how to add a pre-request script to a collection, see [Reuse pre-request scripts](https://learning.postman.com/docs/tests-and-scripts/write-scripts/pre-request-scripts/#reuse-pre-request-scripts).

## Add environment variables

1. [Create an environment](https://learning.postman.com/docs/sending-requests/variables/managing-environments/#create-an-environment).
2. Add the following environment variables to your collection:
   1. `privateKey`: Set it to your API secret (private key).
   2. `apiKey`: Set it to your API key (public key).
   3. `baseUrl`: Set it to `https://api.dev.cobo.com/v2`.

To learn how to set environment variables in Postman, see [Edit and set environment variables in Postman](https://learning.postman.com/docs/sending-requests/variables/environment-variables/).

3. Make sure you have [selected the environment](https://learning.postman.com/docs/sending-requests/variables/managing-environments/#switch-between-environments) you have just created.

## Send an API request

You have now completed the initial setup. The next step is to [send an API request](https://learning.postman.com/docs/sending-requests/create-requests/request-basics/#send-a-request):

1. Choose an operation.
2. Specify any parameters and body data if necessary,
3. Click **Send**. If the request is successful, you will find the response displayed in the response section at the bottom of the page.

<img alt="postman_screenshot" />


# Create key share holder group
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/create-key-share-holder-group

post /wallets/mpc/vaults/{vault_id}/key_share_holder_groups
This operation creates a key share holder group for a specified vault. <Note>This operation will not return the `tss_key_share_groups` property until key shares have been created using the [Create TSS request](https://www.cobo.com/developers/v2/api-references/wallets--mpc-wallets/create-tss-request) operation. Creating a wallet with the [Create wallet](https://www.cobo.com/developers/v2/api-references/wallets/create-wallet) operation is only possible after you've completed the previous actions.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_key_share_holder_group_request import (
      CreateKeyShareHolderGroupRequest,
  )
  from cobo_waas2.models.key_share_holder_group import KeyShareHolderGroup
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      create_key_share_holder_group_request = cobo_waas2.CreateKeyShareHolderGroupRequest(
          key_share_holder_group_type="MainGroup",
          participants=3,
          threshold=2,
          key_share_holders=[
                      cobo_waas2.CreateKeyShareHolder(
                          name="Key share holder name",
                          type="API",
                          tss_node_id="coboAbCdEfGhIjKlMnOpQrStUvWxYz1234567890abcdefghi",
                          signer=True
                      )
                  ]
      )

      try:
          # Create key share holder group
          api_response = api_instance.create_key_share_holder_group(
              vault_id,
              create_key_share_holder_group_request=create_key_share_holder_group_request,
          )
          print("The response of WalletsMPCWalletsApi->create_key_share_holder_group:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->create_key_share_holder_group: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      CreateKeyShareHolderGroupRequest createKeyShareHolderGroupRequest =
            new CreateKeyShareHolderGroupRequest()
                  .keyShareHolderGroupType(KeyShareHolderGroupType.MAINGROUP)
                  .participants(3)
                  .threshold(2)
                  .keyShareHolders(
                    Arrays.asList(
                      new CreateKeyShareHolder()
                      .name("Key share holder name")
                      .type(KeyShareHolderType.API)
                      .tssNodeId("coboAbCdEfGhIjKlMnOpQrStUvWxYz1234567890abcdefghi")
                      .signer(true)
                  ));
      try {
        KeyShareHolderGroup result =
            apiInstance.createKeyShareHolderGroup(vaultId, createKeyShareHolderGroupRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#createKeyShareHolderGroup");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	createKeyShareHolderGroupRequest := *coboWaas2.NewCreateKeyShareHolderGroupRequest(coboWaas2.KeyShareHolderGroupType("MainGroup"), int32(3), int32(2), []coboWaas2.CreateKeyShareHolder{*coboWaas2.NewCreateKeyShareHolder()})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.CreateKeyShareHolderGroup(ctx, vaultId).
  		CreateKeyShareHolderGroupRequest(createKeyShareHolderGroupRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.CreateKeyShareHolderGroup``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateKeyShareHolderGroup`: KeyShareHolderGroup
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `WalletsMPCWalletsAPI.CreateKeyShareHolderGroup`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    CreateKeyShareHolderGroupRequest:
      CoboWaas2.CreateKeyShareHolderGroupRequest.constructFromObject({
        key_share_holder_group_type: "MainGroup",
        participants: 3,
        threshold: 2,
        key_share_holders: [
          {
            name: "Key share holder name",
            type: "API",
            tss_node_id: "coboAbCdEfGhIjKlMnOpQrStUvWxYz1234567890abcdefghi",
            signer: true
          }
        ],
      }),
  };
  apiInstance.createKeyShareHolderGroup(vault_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create project
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/create-project

post /wallets/mpc/projects
This operation creates a project.

<Note>This operation applies to MPC Wallets (User-Controlled Wallets) only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_mpc_project_request import CreateMpcProjectRequest
  from cobo_waas2.models.mpc_project import MPCProject
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      create_mpc_project_request = cobo_waas2.CreateMpcProjectRequest(
          name="Project name", participants=3, threshold=2
      )

      try:
          # Create project
          api_response = api_instance.create_mpc_project(
              create_mpc_project_request=create_mpc_project_request
          )
          print("The response of WalletsMPCWalletsApi->create_mpc_project:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->create_mpc_project: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      CreateMpcProjectRequest createMpcProjectRequest =
          new CreateMpcProjectRequest().name("Project name").participants(3).threshold(2);
      try {
        MPCProject result = apiInstance.createMpcProject(createMpcProjectRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#createMpcProject");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createMpcProjectRequest := *coboWaas2.NewCreateMpcProjectRequest("Project name", int32(3), int32(2))

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.CreateMpcProject(ctx).
  		CreateMpcProjectRequest(createMpcProjectRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.CreateMpcProject``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateMpcProject`: MPCProject
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.CreateMpcProject`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const opts = {
    CreateMpcProjectRequest:
      CoboWaas2.CreateMpcProjectRequest.constructFromObject({
        name: "Project name",
        participants: 3,
        threshold: 2,
      }),
  };
  apiInstance.createMpcProject(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create TSS request
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/create-tss-request

post /wallets/mpc/vaults/{vault_id}/tss_requests
This operation creates a TSS request under a specified vault. You can use this operation to perform actions such as key generation and recovery.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_tss_request_request import CreateTssRequestRequest
  from cobo_waas2.models.tss_request import TSSRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      create_tss_request_request = cobo_waas2.CreateTssRequestRequest(
          type="Recovery",
          target_key_share_holder_group_id="a1bf161f-8b60-4f61-9c35-6434b8654437",
      )

      try:
          # Create TSS request
          api_response = api_instance.create_tss_request(
              vault_id, create_tss_request_request=create_tss_request_request
          )
          print("The response of WalletsMPCWalletsApi->create_tss_request:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->create_tss_request: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      CreateTssRequestRequest createTssRequestRequest =
          new CreateTssRequestRequest()
              .type(TSSRequestType.RECOVERY)
              .targetKeyShareHolderGroupId("a1bf161f-8b60-4f61-9c35-6434b8654437");
      try {
        TSSRequest result = apiInstance.createTssRequest(vaultId, createTssRequestRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#createTssRequest");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	createTssRequestRequest := *coboWaas2.NewCreateTssRequestRequest(coboWaas2.TSSRequestType("KeyGen"), "a1bf161f-8b60-4f61-9c35-6434b8654437")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.CreateTssRequest(ctx, vaultId).
  		CreateTssRequestRequest(createTssRequestRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.CreateTssRequest``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateTssRequest`: TSSRequest
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.CreateTssRequest`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    CreateTssRequestRequest:
      CoboWaas2.CreateTssRequestRequest.constructFromObject({
        type: "Recovery",
        target_key_share_holder_group_id: "a1bf161f-8b60-4f61-9c35-6434b8654437",
      }),
  };
  apiInstance.createTssRequest(vault_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create vault
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/create-vault

post /wallets/mpc/vaults
This operation creates a vault.

<Info>To learn what a vault is and how it relates to MPC Wallets, see [Get started with MPC Wallets](https://www.cobo.com/developers/v2/guides/mpc-wallets/get-started-ocw#technical-architecture).</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_mpc_vault_request import CreateMpcVaultRequest
  from cobo_waas2.models.mpc_vault import MPCVault
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      create_mpc_vault_request = cobo_waas2.CreateMpcVaultRequest(
          name="My vault", vault_type="Org-Controlled"
      )

      try:
          # Create vault
          api_response = api_instance.create_mpc_vault(
              create_mpc_vault_request=create_mpc_vault_request
          )
          print("The response of WalletsMPCWalletsApi->create_mpc_vault:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsMPCWalletsApi->create_mpc_vault: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      CreateMpcVaultRequest createMpcVaultRequest =
          new CreateMpcVaultRequest().name("My vault").vaultType(MPCVaultType.ORG_CONTROLLED);
      try {
        MPCVault result = apiInstance.createMpcVault(createMpcVaultRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#createMpcVault");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createMpcVaultRequest := *coboWaas2.NewCreateMpcVaultRequest("My vault", coboWaas2.MPCVaultType("Org-Controlled"))

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.CreateMpcVault(ctx).
  		CreateMpcVaultRequest(createMpcVaultRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.CreateMpcVault``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateMpcVault`: MPCVault
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.CreateMpcVault`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const opts = {
    CreateMpcVaultRequest: CoboWaas2.CreateMpcVaultRequest.constructFromObject({
      name: "My vault",
      vault_type: "Org-Controlled",
    }),
  };
  apiInstance.createMpcVault(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Delete key share holder group
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/delete-key-share-holder-group

post /wallets/mpc/vaults/{vault_id}/key_share_holder_groups/{key_share_holder_group_id}/delete
This operation deletes a specified key share holder group.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.delete_key_share_holder_group_by_id201_response import (
      DeleteKeyShareHolderGroupById201Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      key_share_holder_group_id = "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce"

      try:
          # Delete key share holder group
          api_response = api_instance.delete_key_share_holder_group_by_id(
              vault_id, key_share_holder_group_id
          )
          print(
              "The response of WalletsMPCWalletsApi->delete_key_share_holder_group_by_id:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->delete_key_share_holder_group_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String keyShareHolderGroupId = "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce";
      try {
        DeleteKeyShareHolderGroupById201Response result =
            apiInstance.deleteKeyShareHolderGroupById(vaultId, keyShareHolderGroupId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling WalletsMpcWalletsApi#deleteKeyShareHolderGroupById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	keyShareHolderGroupId := "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.DeleteKeyShareHolderGroupById(ctx, vaultId, keyShareHolderGroupId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.DeleteKeyShareHolderGroupById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `DeleteKeyShareHolderGroupById`: DeleteKeyShareHolderGroupById201Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `WalletsMPCWalletsAPI.DeleteKeyShareHolderGroupById`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const key_share_holder_group_id = "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce";
  apiInstance
    .deleteKeyShareHolderGroupById(vault_id, key_share_holder_group_id)
    .then(
      (data) => {
        console.log("API called successfully. Returned data: " + data);
      },
      (error) => {
        console.error(error);
      },
    );

  ```
</RequestExample>


# Get key share holder group information
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/get-key-share-holder-group-information

get /wallets/mpc/vaults/{vault_id}/key_share_holder_groups/{key_share_holder_group_id}
This operation retrieves detailed information about a specified key share holder group.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.key_share_holder_group import KeyShareHolderGroup
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      key_share_holder_group_id = "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce"

      try:
          # Get key share holder group information
          api_response = api_instance.get_key_share_holder_group_by_id(
              vault_id, key_share_holder_group_id
          )
          print(
              "The response of WalletsMPCWalletsApi->get_key_share_holder_group_by_id:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->get_key_share_holder_group_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String keyShareHolderGroupId = "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce";
      try {
        KeyShareHolderGroup result =
            apiInstance.getKeyShareHolderGroupById(vaultId, keyShareHolderGroupId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#getKeyShareHolderGroupById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	keyShareHolderGroupId := "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.GetKeyShareHolderGroupById(ctx, vaultId, keyShareHolderGroupId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.GetKeyShareHolderGroupById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetKeyShareHolderGroupById`: KeyShareHolderGroup
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `WalletsMPCWalletsAPI.GetKeyShareHolderGroupById`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const key_share_holder_group_id = "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce";
  apiInstance
    .getKeyShareHolderGroupById(vault_id, key_share_holder_group_id)
    .then(
      (data) => {
        console.log("API called successfully. Returned data: " + data);
      },
      (error) => {
        console.error(error);
      },
    );

  ```
</RequestExample>


# Get key share holder information
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/get-key-share-holder-information

get /wallets/mpc/vaults/{vault_id}/key_share_holders/{tss_node_id}
This operation retrieves detailed information about a specified key share holder.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.key_share_holder import KeyShareHolder
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      tss_node_id = "coboBTGDvjJG99pABegvPYmavrcTU3SkjTLHVdsko8dWBga4w"

      try:
          # Get key share holder information
          api_response = api_instance.get_key_share_holder_by_tss_node_id(
              vault_id, tss_node_id
          )
          print(
              "The response of WalletsMPCWalletsApi->get_key_share_holder_by_tss_node_id:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->get_key_share_holder_by_tss_node_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String tssNodeId = "coboBTGDvjJG99pABegvPYmavrcTU3SkjTLHVdsko8dWBga4w";
      try {
        KeyShareHolder result = apiInstance.getKeyShareHolderByTssNodeId(vaultId, tssNodeId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling WalletsMpcWalletsApi#getKeyShareHolderByTssNodeId");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	tssNodeId := "coboBTGDvjJG99pABegvPYmavrcTU3SkjTLHVdsko8dWBga4w"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.GetKeyShareHolderByTssNodeId(ctx, vaultId, tssNodeId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.GetKeyShareHolderByTssNodeId``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetKeyShareHolderByTssNodeId`: KeyShareHolder
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `WalletsMPCWalletsAPI.GetKeyShareHolderByTssNodeId`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const tss_node_id = "coboBTGDvjJG99pABegvPYmavrcTU3SkjTLHVdsko8dWBga4w";
  apiInstance.getKeyShareHolderByTssNodeId(vault_id, tss_node_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get project information
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/get-project-information

get /wallets/mpc/projects/{project_id}
This operation retrieves detailed information about a project.
<Note>This operation applies to MPC Wallets (User-Controlled Wallets) only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.mpc_project import MPCProject
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      project_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get project information
          api_response = api_instance.get_mpc_project_by_id(project_id)
          print("The response of WalletsMPCWalletsApi->get_mpc_project_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->get_mpc_project_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID projectId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        MPCProject result = apiInstance.getMpcProjectById(projectId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#getMpcProjectById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	projectId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.GetMpcProjectById(ctx, projectId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.GetMpcProjectById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetMpcProjectById`: MPCProject
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.GetMpcProjectById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const project_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getMpcProjectById(project_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get vault information
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/get-vault-information

get /wallets/mpc/vaults/{vault_id}
This operation retrieves detailed information about a vault.

<Info>To learn what a vault is and how it relates to MPC Wallets, see [Get started with MPC Wallets](https://www.cobo.com/developers/v2/guides/mpc-wallets/get-started-ocw#technical-architecture).</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.mpc_vault import MPCVault
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get vault information
          api_response = api_instance.get_mpc_vault_by_id(vault_id)
          print("The response of WalletsMPCWalletsApi->get_mpc_vault_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->get_mpc_vault_by_id: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        MPCVault result = apiInstance.getMpcVaultById(vaultId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#getMpcVaultById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.GetMpcVaultById(ctx, vaultId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.GetMpcVaultById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetMpcVaultById`: MPCVault
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.GetMpcVaultById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getMpcVaultById(vault_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List all Cobo key share holders
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/list-all-cobo-key-share-holders

get /wallets/mpc/cobo_key_share_holders
This operation retrieves a list of all Cobo key share holders and their information. 

<Info>When using this operation, `type` will only return `Cobo` and will never return `Mobile` or `API`.</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.key_share_holder import KeyShareHolder
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)

      try:
          # List all Cobo key share holders
          api_response = api_instance.list_cobo_key_holders()
          print("The response of WalletsMPCWalletsApi->list_cobo_key_holders:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->list_cobo_key_holders: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      try {
        List<KeyShareHolder> result = apiInstance.listCoboKeyHolders();
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#listCoboKeyHolders");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.ListCoboKeyHolders(ctx).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.ListCoboKeyHolders``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListCoboKeyHolders`: []KeyShareHolder
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.ListCoboKeyHolders`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  apiInstance.listCoboKeyHolders().then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List all key share holder groups
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/list-all-key-share-holder-groups

get /wallets/mpc/vaults/{vault_id}/key_share_holder_groups
This operation retrieves all key share holder groups under a specified vault. You can filter the result by group type.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.key_share_holder_group_type import KeyShareHolderGroupType
  from cobo_waas2.models.list_key_share_holder_groups200_response import (
      ListKeyShareHolderGroups200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      key_share_holder_group_type = cobo_waas2.KeyShareHolderGroupType()
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List all key share holder groups
          api_response = api_instance.list_key_share_holder_groups(
              vault_id,
              key_share_holder_group_type=key_share_holder_group_type,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsMPCWalletsApi->list_key_share_holder_groups:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->list_key_share_holder_groups: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      KeyShareHolderGroupType keyShareHolderGroupType =
          KeyShareHolderGroupType.fromValue("MainGroup");
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListKeyShareHolderGroups200Response result =
            apiInstance.listKeyShareHolderGroups(
                vaultId, keyShareHolderGroupType, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#listKeyShareHolderGroups");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	keyShareHolderGroupType := coboWaas2.KeyShareHolderGroupType("MainGroup")
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.ListKeyShareHolderGroups(ctx, vaultId).
  		KeyShareHolderGroupType(keyShareHolderGroupType).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.ListKeyShareHolderGroups``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListKeyShareHolderGroups`: ListKeyShareHolderGroups200Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `WalletsMPCWalletsAPI.ListKeyShareHolderGroups`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    key_share_holder_group_type: new CoboWaas2.KeyShareHolderGroupType(),
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listKeyShareHolderGroups(vault_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List all key share holders
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/list-all-key-share-holders

get /wallets/mpc/vaults/{vault_id}/key_share_holders
This operation retrieves a list of all key share holders under a specified vault. You can filter the result by key share holder group ID.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_key_share_holders200_response import (
      ListKeyShareHolders200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      key_share_holder_group_ids = (
          "dc0cac48-9add-4243-9c7a-b8badac8a198,5558bd1b-d221-4e2b-8c29-f6c97d9e6aca"
      )
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List all key share holders
          api_response = api_instance.list_key_share_holders(
              vault_id,
              key_share_holder_group_ids=key_share_holder_group_ids,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsMPCWalletsApi->list_key_share_holders:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->list_key_share_holders: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String keyShareHolderGroupIds =
          "dc0cac48-9add-4243-9c7a-b8badac8a198,5558bd1b-d221-4e2b-8c29-f6c97d9e6aca";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListKeyShareHolders200Response result =
            apiInstance.listKeyShareHolders(vaultId, keyShareHolderGroupIds, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#listKeyShareHolders");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	keyShareHolderGroupIds := "dc0cac48-9add-4243-9c7a-b8badac8a198,5558bd1b-d221-4e2b-8c29-f6c97d9e6aca"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.ListKeyShareHolders(ctx, vaultId).
  		KeyShareHolderGroupIds(keyShareHolderGroupIds).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.ListKeyShareHolders``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListKeyShareHolders`: ListKeyShareHolders200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.ListKeyShareHolders`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    key_share_holder_group_ids:
      "dc0cac48-9add-4243-9c7a-b8badac8a198,5558bd1b-d221-4e2b-8c29-f6c97d9e6aca",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listKeyShareHolders(vault_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List all projects
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/list-all-projects

get /wallets/mpc/projects
This operation retrieves a list of all projects.

<Note>This operation applies to MPC Wallets (User-Controlled Wallets) only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_mpc_projects200_response import ListMpcProjects200Response
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List all projects
          api_response = api_instance.list_mpc_projects(
              limit=limit, before=before, after=after
          )
          print("The response of WalletsMPCWalletsApi->list_mpc_projects:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->list_mpc_projects: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListMpcProjects200Response result = apiInstance.listMpcProjects(limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#listMpcProjects");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.ListMpcProjects(ctx).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.ListMpcProjects``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListMpcProjects`: ListMpcProjects200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.ListMpcProjects`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const opts = {
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listMpcProjects(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List all vaults
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/list-all-vaults

get /wallets/mpc/vaults
This operation retrieves a list of all vaults. You can filter the result by project ID.

**Notes for query parameters**:
1. `project_id` is required when `vault_type` is set to `User-Controlled`.
2. `project_id` must be left blank when `vault_type` is set to `Org-Controlled`.

<Info>To learn what a vault is and how it relates to MPC Wallets, see [Get started with MPC Wallets](https://www.cobo.com/developers/v2/guides/mpc-wallets/get-started-ocw#technical-architecture).</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_mpc_vaults200_response import ListMpcVaults200Response
  from cobo_waas2.models.mpc_vault_type import MPCVaultType
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_type = cobo_waas2.MPCVaultType()
      project_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List all vaults
          api_response = api_instance.list_mpc_vaults(
              vault_type, project_id=project_id, limit=limit, before=before, after=after
          )
          print("The response of WalletsMPCWalletsApi->list_mpc_vaults:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsMPCWalletsApi->list_mpc_vaults: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      MPCVaultType vaultType = MPCVaultType.fromValue("Org-Controlled");
      UUID projectId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListMpcVaults200Response result =
            apiInstance.listMpcVaults(vaultType, projectId, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#listMpcVaults");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultType := coboWaas2.MPCVaultType("Org-Controlled")
  	projectId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.ListMpcVaults(ctx).
  		VaultType(vaultType).
  		ProjectId(projectId).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.ListMpcVaults``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListMpcVaults`: ListMpcVaults200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.ListMpcVaults`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_type = new CoboWaas2.MPCVaultType();
  const opts = {
    project_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listMpcVaults(vault_type, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List TSS requests
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/list-tss-requests

get /wallets/mpc/vaults/{vault_id}/tss_requests
This operation retrieves a list of TSS requests and their details.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_tss_requests200_response import ListTssRequests200Response
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      key_share_holder_group_id = "a3a45e99-5a12-444f-867a-ffe0ebb1bb30"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List TSS requests
          api_response = api_instance.list_tss_requests(
              vault_id, key_share_holder_group_id, limit=limit, before=before, after=after
          )
          print("The response of WalletsMPCWalletsApi->list_tss_requests:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->list_tss_requests: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String keyShareHolderGroupId = "a3a45e99-5a12-444f-867a-ffe0ebb1bb30";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListTssRequests200Response result =
            apiInstance.listTssRequests(vaultId, keyShareHolderGroupId, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#listTssRequests");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	keyShareHolderGroupId := "a3a45e99-5a12-444f-867a-ffe0ebb1bb30"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.ListTssRequests(ctx, vaultId).
  		KeyShareHolderGroupId(keyShareHolderGroupId).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.ListTssRequests``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTssRequests`: ListTssRequests200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.ListTssRequests`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const key_share_holder_group_id = "a3a45e99-5a12-444f-867a-ffe0ebb1bb30";
  const opts = {
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listTssRequests(vault_id, key_share_holder_group_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Update key share holder group
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/update-key-share-holder-group

put /wallets/mpc/vaults/{vault_id}/key_share_holder_groups/{key_share_holder_group_id}
This operation updates a specified active [Signing Group](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/create-key-share-groups). For example, you can use this operation to upgrade a Signing Group to the [Main Group](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/create-key-share-groups).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.key_share_holder_group import KeyShareHolderGroup
  from cobo_waas2.models.update_key_share_holder_group_by_id_request import (
      UpdateKeyShareHolderGroupByIdRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      key_share_holder_group_id = "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce"
      update_key_share_holder_group_by_id_request = (
          cobo_waas2.UpdateKeyShareHolderGroupByIdRequest(
              update_key_share_holder_group_action="UpgradeToMainGroup"
          )
      )

      try:
          # Update key share holder group
          api_response = api_instance.update_key_share_holder_group_by_id(
              vault_id,
              key_share_holder_group_id,
              update_key_share_holder_group_by_id_request=update_key_share_holder_group_by_id_request,
          )
          print(
              "The response of WalletsMPCWalletsApi->update_key_share_holder_group_by_id:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->update_key_share_holder_group_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String keyShareHolderGroupId = "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce";
      UpdateKeyShareHolderGroupByIdRequest updateKeyShareHolderGroupByIdRequest =
          new UpdateKeyShareHolderGroupByIdRequest()
              .updateKeyShareHolderGroupAction(UpdateGroupAction.UPGRADETOMAINGROUP);
      try {
        KeyShareHolderGroup result =
            apiInstance.updateKeyShareHolderGroupById(
                vaultId, keyShareHolderGroupId, updateKeyShareHolderGroupByIdRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling WalletsMpcWalletsApi#updateKeyShareHolderGroupById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	keyShareHolderGroupId := "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce"
  	updateKeyShareHolderGroupByIdRequest := *coboWaas2.NewUpdateKeyShareHolderGroupByIdRequest(coboWaas2.UpdateGroupAction("UpgradeToMainGroup"))

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.UpdateKeyShareHolderGroupById(ctx, vaultId, keyShareHolderGroupId).
  		UpdateKeyShareHolderGroupByIdRequest(updateKeyShareHolderGroupByIdRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.UpdateKeyShareHolderGroupById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UpdateKeyShareHolderGroupById`: KeyShareHolderGroup
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `WalletsMPCWalletsAPI.UpdateKeyShareHolderGroupById`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const key_share_holder_group_id = "e8257ac8-76b8-4d1e-a1f9-eec4cb931dce";
  const opts = {
    UpdateKeyShareHolderGroupByIdRequest:
      CoboWaas2.UpdateKeyShareHolderGroupByIdRequest.constructFromObject({
        update_key_share_holder_group_action: "UpgradeToMainGroup",
        original_main_group_handling: "Invalidate",
      }),
  };
  apiInstance
    .updateKeyShareHolderGroupById(vault_id, key_share_holder_group_id, opts)
    .then(
      (data) => {
        console.log("API called successfully. Returned data: " + data);
      },
      (error) => {
        console.error(error);
      },
    );

  ```
</RequestExample>


# Update project name
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/update-project-name

put /wallets/mpc/projects/{project_id}
This operation updates a project's name.

<Note>This operation applies to MPC Wallets (User-Controlled Wallets) only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.mpc_project import MPCProject
  from cobo_waas2.models.update_mpc_project_by_id_request import (
      UpdateMpcProjectByIdRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      project_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      update_mpc_project_by_id_request = cobo_waas2.UpdateMpcProjectByIdRequest(
          name="New project name"
      )

      try:
          # Update project name
          api_response = api_instance.update_mpc_project_by_id(
              project_id,
              update_mpc_project_by_id_request=update_mpc_project_by_id_request,
          )
          print("The response of WalletsMPCWalletsApi->update_mpc_project_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->update_mpc_project_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID projectId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      UpdateMpcProjectByIdRequest updateMpcProjectByIdRequest =
          new UpdateMpcProjectByIdRequest().name("New project name");
      try {
        MPCProject result = apiInstance.updateMpcProjectById(projectId, updateMpcProjectByIdRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#updateMpcProjectById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	projectId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	updateMpcProjectByIdRequest := *coboWaas2.NewUpdateMpcProjectByIdRequest("New project name")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.UpdateMpcProjectById(ctx, projectId).
  		UpdateMpcProjectByIdRequest(updateMpcProjectByIdRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.UpdateMpcProjectById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UpdateMpcProjectById`: MPCProject
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.UpdateMpcProjectById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const project_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    UpdateMpcProjectByIdRequest:
      CoboWaas2.UpdateMpcProjectByIdRequest.constructFromObject({
        name: "New project name",
      }),
  };
  apiInstance.updateMpcProjectById(project_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Update vault name
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/update-vault-name

put /wallets/mpc/vaults/{vault_id}
This operation updates a vault's name.

<Info>To learn what a vault is and how it relates to MPC Wallets, see [Get started with MPC Wallets](https://www.cobo.com/developers/v2/guides/mpc-wallets/get-started-ocw#technical-architecture).</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.mpc_vault import MPCVault
  from cobo_waas2.models.update_mpc_vault_by_id_request import UpdateMpcVaultByIdRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      update_mpc_vault_by_id_request = cobo_waas2.UpdateMpcVaultByIdRequest(
          name="The new name of the vault"
      )

      try:
          # Update vault name
          api_response = api_instance.update_mpc_vault_by_id(
              vault_id, update_mpc_vault_by_id_request=update_mpc_vault_by_id_request
          )
          print("The response of WalletsMPCWalletsApi->update_mpc_vault_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->update_mpc_vault_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      UpdateMpcVaultByIdRequest updateMpcVaultByIdRequest =
          new UpdateMpcVaultByIdRequest().name("The new name of the vault");
      try {
        MPCVault result = apiInstance.updateMpcVaultById(vaultId, updateMpcVaultByIdRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#updateMpcVaultById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	updateMpcVaultByIdRequest := *coboWaas2.NewUpdateMpcVaultByIdRequest("The new name of the vault")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.UpdateMpcVaultById(ctx, vaultId).
  		UpdateMpcVaultByIdRequest(updateMpcVaultByIdRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.UpdateMpcVaultById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UpdateMpcVaultById`: MPCVault
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.UpdateMpcVaultById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    UpdateMpcVaultByIdRequest:
      CoboWaas2.UpdateMpcVaultByIdRequest.constructFromObject({
        name: "The new name of the vault",
      }),
  };
  apiInstance.updateMpcVaultById(vault_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Batch check UTXOs
Source: https://cobo.com/developers/v2/api-references/wallets/batch-check-utxos

post /wallets/{wallet_id}/utxos/batch_check
This operation verifies the existence and details of specified **unspent** transaction outputs (UTXOs) for a given wallet and token. A maximum of 100 UTXOs can be verified per request.

<Note>This operation returns only UTXOs that are not used by any transaction. It does not return all UTXOs.</Note>

<Info>This operation is applicable to MPC Wallets and Custodial Wallets (Web3 Wallets) only.</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.batch_check_utxo201_response import BatchCheckUtxo201Response
  from cobo_waas2.models.batch_check_utxo_request import BatchCheckUtxoRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      batch_check_utxo_request = cobo_waas2.BatchCheckUtxoRequest(
          token_id="BTC",
          utxos=[
              cobo_waas2.BatchUTXOParam(
                  tx_hash="9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb"
              )
          ],
      )

      try:
          # Batch check UTXOs
          api_response = api_instance.batch_check_utxo(
              wallet_id, batch_check_utxo_request=batch_check_utxo_request
          )
          print("The response of WalletsApi->batch_check_utxo:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->batch_check_utxo: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      BatchCheckUtxoRequest batchCheckUtxoRequest =
          new BatchCheckUtxoRequest()
              .tokenId("BTC")
              .utxos(
                  Arrays.asList(
                      new BatchUTXOParam()
                          .txHash(
                              "9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb")));
      try {
        BatchCheckUtxo201Response result =
            apiInstance.batchCheckUtxo(walletId, batchCheckUtxoRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#batchCheckUtxo");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	batchCheckUtxoRequest := *coboWaas2.NewBatchCheckUtxoRequest("BTC", []coboWaas2.BatchUTXOParam{*coboWaas2.NewBatchUTXOParam("9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.BatchCheckUtxo(ctx, walletId).
  		BatchCheckUtxoRequest(batchCheckUtxoRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.BatchCheckUtxo``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `BatchCheckUtxo`: BatchCheckUtxo201Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.BatchCheckUtxo`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    BatchCheckUtxoRequest: CoboWaas2.BatchCheckUtxoRequest.constructFromObject({
      token_id: "BTC",
      utxos: [
        {
          tx_hash:
            "9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb",
        },
      ],
    }),
  };
  apiInstance.batchCheckUtxo(wallet_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Check address validity
Source: https://cobo.com/developers/v2/api-references/wallets/check-address-validity

get /wallets/check_address_validity
This operation verifies if a given address is valid for a specific chain.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.check_address_validity200_response import (
      CheckAddressValidity200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      chain_id = "ETH"
      address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"

      try:
          # Check address validity
          api_response = api_instance.check_address_validity(chain_id, address)
          print("The response of WalletsApi->check_address_validity:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->check_address_validity: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      String chainId = "ETH";
      String address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045";
      try {
        CheckAddressValidity200Response result = apiInstance.checkAddressValidity(chainId, address);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#checkAddressValidity");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	chainId := "ETH"
  	address := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.CheckAddressValidity(ctx).
  		ChainId(chainId).
  		Address(address).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.CheckAddressValidity``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CheckAddressValidity`: CheckAddressValidity200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.CheckAddressValidity`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const chain_id = "ETH";
  const address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045";
  apiInstance.checkAddressValidity(chain_id, address).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Check address validity across chains
Source: https://cobo.com/developers/v2/api-references/wallets/check-address-validity-across-chains

get /wallets/check_address_chains_validity
This operation verifies if a given address is valid for a list of chains.

<Note>You can specify up to 20 chain IDs in a single request.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.check_address_chains_validity200_response_inner import (
      CheckAddressChainsValidity200ResponseInner,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
      chain_ids = "BTC,ETH"

      try:
          # Check address validity across chains
          api_response = api_instance.check_address_chains_validity(address, chain_ids)
          print("The response of WalletsApi->check_address_chains_validity:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsApi->check_address_chains_validity: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      String address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045";
      String chainIds = "BTC,ETH";
      try {
        List<CheckAddressChainsValidity200ResponseInner> result =
            apiInstance.checkAddressChainsValidity(address, chainIds);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#checkAddressChainsValidity");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	address := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
  	chainIds := "BTC,ETH"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.CheckAddressChainsValidity(ctx).
  		Address(address).
  		ChainIds(chainIds).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsAPI.CheckAddressChainsValidity``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CheckAddressChainsValidity`: []CheckAddressChainsValidity200ResponseInner
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.CheckAddressChainsValidity`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045";
  const chain_ids = "BTC,ETH";
  apiInstance.checkAddressChainsValidity(address, chain_ids).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Check addresses validity
Source: https://cobo.com/developers/v2/api-references/wallets/check-addresses-validity

get /wallets/check_addresses_validity
This operation verifies if given addresses are valid for a specific chain.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.check_addresses_validity200_response_inner import (
      CheckAddressesValidity200ResponseInner,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      chain_id = "ETH"
      addresses = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97"

      try:
          # Check addresses validity
          api_response = api_instance.check_addresses_validity(chain_id, addresses)
          print("The response of WalletsApi->check_addresses_validity:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->check_addresses_validity: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      String chainId = "ETH";
      String addresses =
          "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97";
      try {
        List<CheckAddressesValidity200ResponseInner> result =
            apiInstance.checkAddressesValidity(chainId, addresses);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#checkAddressesValidity");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	chainId := "ETH"
  	addresses := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.CheckAddressesValidity(ctx).
  		ChainId(chainId).
  		Addresses(addresses).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.CheckAddressesValidity``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CheckAddressesValidity`: []CheckAddressesValidity200ResponseInner
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.CheckAddressesValidity`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const chain_id = "ETH";
  const addresses =
    "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97";
  apiInstance.checkAddressesValidity(chain_id, addresses).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create addresses in wallet
Source: https://cobo.com/developers/v2/api-references/wallets/create-addresses-in-wallet

post /wallets/{wallet_id}/addresses
This operation generates one or more addresses within a specified wallet.

<Note>This operation is applicable to Custodial Wallets and MPC Wallets only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.address_info import AddressInfo
  from cobo_waas2.models.create_address_request import CreateAddressRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      create_address_request = cobo_waas2.CreateAddressRequest(chain_id="ETH", count=1)

      try:
          # Create addresses in wallet
          api_response = api_instance.create_address(
              wallet_id, create_address_request=create_address_request
          )
          print("The response of WalletsApi->create_address:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->create_address: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      CreateAddressRequest createAddressRequest = new CreateAddressRequest().chainId("ETH").count(1);
      try {
        List<AddressInfo> result = apiInstance.createAddress(walletId, createAddressRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#createAddress");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	createAddressRequest := *coboWaas2.NewCreateAddressRequest("ETH", int32(1))

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.CreateAddress(ctx, walletId).
  		CreateAddressRequest(createAddressRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.CreateAddress``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateAddress`: []AddressInfo
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.CreateAddress`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    CreateAddressRequest: CoboWaas2.CreateAddressRequest.constructFromObject({
      chain_id: "ETH",
      count: 1,
    }),
  };
  apiInstance.createAddress(wallet_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create token listing request
Source: https://cobo.com/developers/v2/api-references/wallets/create-token-listing-request

post /wallets/tokens/listing_requests
This operation creates a token listing request. The token to be listed must already be deployed on the specified blockchain and have a valid contract address.

<note>Currently, tokens listed through this operation are only supported in wallets of type `Custodial` or `MPC`, and subtype `Asset`, `Web3`, or `Org-Controlled`.</note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_token_listing_request201_response import (
      CreateTokenListingRequest201Response,
  )
  from cobo_waas2.models.create_token_listing_request_request import (
      CreateTokenListingRequestRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      create_token_listing_request_request = cobo_waas2.CreateTokenListingRequestRequest(
          wallet_type="Custodial",
          wallet_subtype="Asset",
          chain_id="ETH",
          contract_address="0x6B175474E89094C44Da98b954EedeAC495271d0F",
      )

      try:
          # Create token listing request
          api_response = api_instance.create_token_listing_request(
              create_token_listing_request_request
          )
          print("The response of WalletsApi->create_token_listing_request:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsApi->create_token_listing_request: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      CreateTokenListingRequestRequest createTokenListingRequestRequest =
          new CreateTokenListingRequestRequest()
              .walletType(WalletType.CUSTODIAL)
              .walletSubtype(WalletSubtype.ASSET)
              .chainId("ETH")
              .contractAddress("0x6B175474E89094C44Da98b954EedeAC495271d0F");
      try {
        CreateTokenListingRequest201Response result =
            apiInstance.createTokenListingRequest(createTokenListingRequestRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#createTokenListingRequest");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createTokenListingRequestRequest := *coboWaas2.NewCreateTokenListingRequestRequest(coboWaas2.WalletType("Custodial"), coboWaas2.WalletSubtype("Asset"), "ETH", "0x6B175474E89094C44Da98b954EedeAC495271d0F")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.CreateTokenListingRequest(ctx).
  		CreateTokenListingRequestRequest(createTokenListingRequestRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsAPI.CreateTokenListingRequest``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateTokenListingRequest`: CreateTokenListingRequest201Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.CreateTokenListingRequest`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const CreateTokenListingRequestRequest =
    new CoboWaas2.CreateTokenListingRequestRequest();
  apiInstance.createTokenListingRequest(CreateTokenListingRequestRequest).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create wallet
Source: https://cobo.com/developers/v2/api-references/wallets/create-wallet

post /wallets
This operation creates a wallet with the provided information.

<Note>This operation is not applicable to Smart Contract Wallets.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_wallet_params import CreateWalletParams
  from cobo_waas2.models.created_wallet_info import CreatedWalletInfo
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      create_wallet_params = cobo_waas2.CreateWalletParams(
          cobo_waas2.CreateCustodialWalletParams(
              name="My WaaS 2.0 Wallet", wallet_type="Custodial", wallet_subtype="Asset"
          )
      )

      try:
          # Create wallet
          api_response = api_instance.create_wallet(
              create_wallet_params=create_wallet_params
          )
          print("The response of WalletsApi->create_wallet:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->create_wallet: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      CreateWalletParams createWalletParams =
          new CreateWalletParams(
              new CreateCustodialWalletParams()
                  .name("My WaaS 2.0 Wallet")
                  .walletType(WalletType.CUSTODIAL)
                  .walletSubtype(WalletSubtype.ASSET));
      try {
        CreatedWalletInfo result = apiInstance.createWallet(createWalletParams);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#createWallet");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createWalletParams := coboWaas2.CreateWalletParams{
  		CreateCustodialWalletParams: coboWaas2.NewCreateCustodialWalletParams(
  			"My WaaS 2.0 Wallet",
  			coboWaas2.WalletType("Custodial"),
  			coboWaas2.WalletSubtype("Asset"),
  		),
  	}

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.CreateWallet(ctx).
  		CreateWalletParams(createWalletParams).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.CreateWallet``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateWallet`: CreatedWalletInfo
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.CreateWallet`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const opts = {
    CreateWalletParams: CoboWaas2.CreateWalletParams.constructFromObject({
      name: "My WaaS 2.0 Wallet",
      wallet_type: "Custodial",
      wallet_subtype: "Asset",
    }),
  };
  apiInstance.createWallet(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Delete wallet
Source: https://cobo.com/developers/v2/api-references/wallets/delete-wallet

post /wallets/{wallet_id}/delete
This operation deletes a specified wallet.

<Note>This operation is applicable to Exchange Wallets only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.delete_wallet_by_id201_response import (
      DeleteWalletById201Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Delete wallet
          api_response = api_instance.delete_wallet_by_id(wallet_id)
          print("The response of WalletsApi->delete_wallet_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->delete_wallet_by_id: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        DeleteWalletById201Response result = apiInstance.deleteWalletById(walletId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#deleteWalletById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.DeleteWalletById(ctx, walletId).Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.DeleteWalletById``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `DeleteWalletById`: DeleteWalletById201Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.DeleteWalletById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.deleteWalletById(wallet_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Estimate maximum transferable value
Source: https://cobo.com/developers/v2/api-references/wallets/estimate-maximum-transferable-value

post /wallets/{wallet_id}/max_transferable_value_with_fee_model
This operation estimates the maximum transferable value from a wallet or a specific wallet address, based on the specified fee settings.

The `to_address` property is required because it affects the fee calculation.

<Note>This operation is applicable to Custodial Wallets (Web3 Wallets) and MPC Wallets only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.get_max_transferable_value_with_fee_model_request import (
      GetMaxTransferableValueWithFeeModelRequest,
  )
  from cobo_waas2.models.max_transferable_value import MaxTransferableValue
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      get_max_transferable_value_with_fee_model_request = (
          cobo_waas2.GetMaxTransferableValueWithFeeModelRequest(
              token_id="ETH_USDT",
              fee=cobo_waas2.TransactionRequestFee(
                  cobo_waas2.TransactionRequestFixedFee(
                      fee_type="EVM_EIP_1559", token_id="TRON"
                  )
              ),
              to_address="2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE",
          )
      )

      try:
          # Estimate maximum transferable value
          api_response = api_instance.get_max_transferable_value_with_fee_model(
              wallet_id,
              get_max_transferable_value_with_fee_model_request=get_max_transferable_value_with_fee_model_request,
          )
          print(
              "The response of WalletsApi->get_max_transferable_value_with_fee_model:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsApi->get_max_transferable_value_with_fee_model: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      GetMaxTransferableValueWithFeeModelRequest getMaxTransferableValueWithFeeModelRequest =
          new GetMaxTransferableValueWithFeeModelRequest()
              .tokenId("ETH_USDT")
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee().feeType(FeeType.EVM_EIP_1559).tokenId("TRON")))
              .toAddress("2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE");
      try {
        MaxTransferableValue result =
            apiInstance.getMaxTransferableValueWithFeeModel(
                walletId, getMaxTransferableValueWithFeeModelRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#getMaxTransferableValueWithFeeModel");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	getMaxTransferableValueWithFeeModelRequest := *coboWaas2.NewGetMaxTransferableValueWithFeeModelRequest("ETH_USDT", coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")}, "2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.GetMaxTransferableValueWithFeeModel(ctx, walletId).
  		GetMaxTransferableValueWithFeeModelRequest(getMaxTransferableValueWithFeeModelRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsAPI.GetMaxTransferableValueWithFeeModel``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetMaxTransferableValueWithFeeModel`: MaxTransferableValue
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `WalletsAPI.GetMaxTransferableValueWithFeeModel`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    GetMaxTransferableValueWithFeeModelRequest:
      CoboWaas2.GetMaxTransferableValueWithFeeModelRequest.constructFromObject({
        token_id: "ETH_USDT",
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
        to_address: "2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE",
      }),
  };
  apiInstance.getMaxTransferableValueWithFeeModel(wallet_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get chain information
Source: https://cobo.com/developers/v2/api-references/wallets/get-chain-information

get /wallets/chains/{chain_id}
This operation retrieves the detailed information about a specified chain.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.chain_info import ChainInfo
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      chain_id = "ETH"

      try:
          # Get chain information
          api_response = api_instance.get_chain_by_id(chain_id)
          print("The response of WalletsApi->get_chain_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->get_chain_by_id: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      String chainId = "ETH";
      try {
        ChainInfo result = apiInstance.getChainById(chainId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#getChainById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	chainId := "ETH"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.GetChainById(ctx, chainId).Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.GetChainById``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetChainById`: ChainInfo
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.GetChainById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const chain_id = "ETH";
  apiInstance.getChainById(chain_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get maximum transferable value
Source: https://cobo.com/developers/v2/api-references/wallets/get-maximum-transferable-value

get /wallets/{wallet_id}/max_transferable_value
<Warning>This operation is planned for deprecation. We recommend using  [Estimate maximum transferable value](https://www.cobo.com/developers/v2/api-references/wallets/estimate-maximum-transferable-value) instead.</Warning>
This operation retrieves the maximum amount that you can transfer from a wallet or a specified wallet address, along with the corresponding transaction fee.

You must specify `to_address` in your query because it affects the transaction fee.

<Note>This operation is applicable to Custodial Wallets and MPC Wallets only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.max_transferable_value import MaxTransferableValue
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      token_id = "ETH_USDT"
      fee_rate = "10"
      to_address = "2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE"
      from_address = "2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE"

      try:
          # Get maximum transferable value
          api_response = api_instance.get_max_transferable_value(
              wallet_id, token_id, fee_rate, to_address, from_address=from_address
          )
          print("The response of WalletsApi->get_max_transferable_value:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->get_max_transferable_value: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String tokenId = "ETH_USDT";
      String feeRate = "10";
      String toAddress = "2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE";
      String fromAddress = "2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE";
      try {
        MaxTransferableValue result =
            apiInstance.getMaxTransferableValue(walletId, tokenId, feeRate, toAddress, fromAddress);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#getMaxTransferableValue");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	tokenId := "ETH_USDT"
  	feeRate := "10"
  	toAddress := "2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE"
  	fromAddress := "2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.GetMaxTransferableValue(ctx, walletId).
  		TokenId(tokenId).
  		FeeRate(feeRate).
  		ToAddress(toAddress).
  		FromAddress(fromAddress).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsAPI.GetMaxTransferableValue``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetMaxTransferableValue`: MaxTransferableValue
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.GetMaxTransferableValue`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const token_id = "ETH_USDT";
  const fee_rate = "10";
  const to_address = "2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE";
  const opts = {
    from_address: "2N2xFZtbCFB6Nb3Pj9Sxsx5mX2fxX3yEgkE",
  };
  apiInstance
    .getMaxTransferableValue(wallet_id, token_id, fee_rate, to_address, opts)
    .then(
      (data) => {
        console.log("API called successfully. Returned data: " + data);
      },
      (error) => {
        console.error(error);
      },
    );

  ```
</RequestExample>


# Get token information
Source: https://cobo.com/developers/v2/api-references/wallets/get-token-information

get /wallets/tokens/{token_id}
This operation retrieves the detailed information about a specified token.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.extended_token_info import ExtendedTokenInfo
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      token_id = "ETH_USDT"

      try:
          # Get token information
          api_response = api_instance.get_token_by_id(token_id)
          print("The response of WalletsApi->get_token_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->get_token_by_id: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      String tokenId = "ETH_USDT";
      try {
        ExtendedTokenInfo result = apiInstance.getTokenById(tokenId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#getTokenById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.GetTokenById(ctx, tokenId).Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.GetTokenById``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetTokenById`: ExtendedTokenInfo
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.GetTokenById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const token_id = "ETH_USDT";
  apiInstance.getTokenById(token_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get token listing request
Source: https://cobo.com/developers/v2/api-references/wallets/get-token-listing-request

get /wallets/tokens/listing_requests/{request_id}
This operation retrieves detailed information about a specific token listing request, including its current status.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.token_listing import TokenListing
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      request_id = "123e4567e89b12d3a456426614174000"

      try:
          # Get token listing request
          api_response = api_instance.get_token_listing_request_by_request_id(request_id)
          print("The response of WalletsApi->get_token_listing_request_by_request_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsApi->get_token_listing_request_by_request_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      String requestId = "123e4567e89b12d3a456426614174000";
      try {
        TokenListing result = apiInstance.getTokenListingRequestByRequestId(requestId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#getTokenListingRequestByRequestId");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	requestId := "123e4567e89b12d3a456426614174000"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.GetTokenListingRequestByRequestId(ctx, requestId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsAPI.GetTokenListingRequestByRequestId``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetTokenListingRequestByRequestId`: TokenListing
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `WalletsAPI.GetTokenListingRequestByRequestId`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const request_id = "123e4567e89b12d3a456426614174000";
  apiInstance.getTokenListingRequestByRequestId(request_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get wallet information
Source: https://cobo.com/developers/v2/api-references/wallets/get-wallet-information

get /wallets/{wallet_id}
This operation retrieves the detailed information about a specified wallet.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.wallet_info import WalletInfo
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get wallet information
          api_response = api_instance.get_wallet_by_id(wallet_id)
          print("The response of WalletsApi->get_wallet_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->get_wallet_by_id: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        WalletInfo result = apiInstance.getWalletById(walletId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#getWalletById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.GetWalletById(ctx, walletId).Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.GetWalletById``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetWalletById`: WalletInfo
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.GetWalletById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getWalletById(wallet_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List address balances by token
Source: https://cobo.com/developers/v2/api-references/wallets/list-address-balances-by-token

get /wallets/{wallet_id}/tokens/{token_id}
This operation retrieves a list of address balances for a specified token within a wallet.

<Note>This operation is applicable to MPC Wallets and Custodial Wallets (Web3 Wallets) only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_address_balances_by_token200_response import (
      ListAddressBalancesByToken200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      token_id = "ETH_USDT"
      addresses = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List address balances by token
          api_response = api_instance.list_address_balances_by_token(
              wallet_id,
              token_id,
              addresses=addresses,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsApi->list_address_balances_by_token:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsApi->list_address_balances_by_token: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String tokenId = "ETH_USDT";
      String addresses =
          "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListAddressBalancesByToken200Response result =
            apiInstance.listAddressBalancesByToken(
                walletId, tokenId, addresses, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listAddressBalancesByToken");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	tokenId := "ETH_USDT"
  	addresses := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListAddressBalancesByToken(ctx, walletId, tokenId).
  		Addresses(addresses).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsAPI.ListAddressBalancesByToken``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListAddressBalancesByToken`: ListAddressBalancesByToken200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListAddressBalancesByToken`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const token_id = "ETH_USDT";
  const opts = {
    addresses:
      "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listAddressBalancesByToken(wallet_id, token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List all wallets
Source: https://cobo.com/developers/v2/api-references/wallets/list-all-wallets

get /wallets
This operation retrieves the information of all wallets under your organization. You can filter the result by wallet type and subtype. For MPC Wallets, you can also filter by project ID and vault ID.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_wallets200_response import ListWallets200Response
  from cobo_waas2.models.wallet_subtype import WalletSubtype
  from cobo_waas2.models.wallet_type import WalletType
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_type = cobo_waas2.WalletType()
      wallet_subtype = cobo_waas2.WalletSubtype()
      project_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List all wallets
          api_response = api_instance.list_wallets(
              wallet_type=wallet_type,
              wallet_subtype=wallet_subtype,
              project_id=project_id,
              vault_id=vault_id,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsApi->list_wallets:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->list_wallets: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      WalletType walletType = WalletType.fromValue("Custodial");
      WalletSubtype walletSubtype = WalletSubtype.fromValue("Asset");
      UUID projectId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListWallets200Response result =
            apiInstance.listWallets(
                walletType, walletSubtype, projectId, vaultId, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listWallets");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletType := coboWaas2.WalletType("Custodial")
  	walletSubtype := coboWaas2.WalletSubtype("Asset")
  	projectId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListWallets(ctx).
  		WalletType(walletType).
  		WalletSubtype(walletSubtype).
  		ProjectId(projectId).
  		VaultId(vaultId).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.ListWallets``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListWallets`: ListWallets200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListWallets`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const opts = {
    wallet_type: "Custodial",
    wallet_subtype: "Asset",
    project_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
    vault_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listWallets(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List enabled chains
Source: https://cobo.com/developers/v2/api-references/wallets/list-enabled-chains

get /wallets/enabled_chains
This operation retrieves all the chains that can be used by your organization. 

You can filter the result by wallet type or subtype. If you do not specify a wallet type, this operation returns a combination of chains that can be used by your organization for each wallet type.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_supported_chains200_response import (
      ListSupportedChains200Response,
  )
  from cobo_waas2.models.wallet_subtype import WalletSubtype
  from cobo_waas2.models.wallet_type import WalletType
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_type = cobo_waas2.WalletType()
      wallet_subtype = cobo_waas2.WalletSubtype()
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List enabled chains
          api_response = api_instance.list_enabled_chains(
              wallet_type=wallet_type,
              wallet_subtype=wallet_subtype,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsApi->list_enabled_chains:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->list_enabled_chains: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      WalletType walletType = WalletType.fromValue("Custodial");
      WalletSubtype walletSubtype = WalletSubtype.fromValue("Asset");
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListSupportedChains200Response result =
            apiInstance.listEnabledChains(walletType, walletSubtype, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listEnabledChains");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletType := coboWaas2.WalletType("Custodial")
  	walletSubtype := coboWaas2.WalletSubtype("Asset")
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListEnabledChains(ctx).
  		WalletType(walletType).
  		WalletSubtype(walletSubtype).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.ListEnabledChains``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListEnabledChains`: ListSupportedChains200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListEnabledChains`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const opts = {
    wallet_type: "Custodial",
    wallet_subtype: "Asset",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listEnabledChains(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List enabled tokens
Source: https://cobo.com/developers/v2/api-references/wallets/list-enabled-tokens

get /wallets/enabled_tokens
This operation retrieves all the tokens that can be used by your organization. 

You can filter the result by wallet type, subtype, chain IDs, and token IDs. If you do not specify a wallet type, this operation returns a combination of tokens that can be used by your organization for each wallet type.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_supported_tokens200_response import (
      ListSupportedTokens200Response,
  )
  from cobo_waas2.models.wallet_subtype import WalletSubtype
  from cobo_waas2.models.wallet_type import WalletType
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_type = cobo_waas2.WalletType()
      wallet_subtype = cobo_waas2.WalletSubtype()
      chain_ids = "BTC,ETH"
      token_ids = "ETH_USDT,ETH_USDC"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List enabled tokens
          api_response = api_instance.list_enabled_tokens(
              wallet_type=wallet_type,
              wallet_subtype=wallet_subtype,
              chain_ids=chain_ids,
              token_ids=token_ids,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsApi->list_enabled_tokens:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->list_enabled_tokens: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      WalletType walletType = WalletType.fromValue("Custodial");
      WalletSubtype walletSubtype = WalletSubtype.fromValue("Asset");
      String chainIds = "BTC,ETH";
      String tokenIds = "ETH_USDT,ETH_USDC";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListSupportedTokens200Response result =
            apiInstance.listEnabledTokens(
                walletType, walletSubtype, chainIds, tokenIds, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listEnabledTokens");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletType := coboWaas2.WalletType("Custodial")
  	walletSubtype := coboWaas2.WalletSubtype("Asset")
  	chainIds := "BTC,ETH"
  	tokenIds := "ETH_USDT,ETH_USDC"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListEnabledTokens(ctx).
  		WalletType(walletType).
  		WalletSubtype(walletSubtype).
  		ChainIds(chainIds).
  		TokenIds(tokenIds).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.ListEnabledTokens``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListEnabledTokens`: ListSupportedTokens200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListEnabledTokens`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const opts = {
    wallet_type: "Custodial",
    wallet_subtype: "Asset",
    chain_ids: "BTC,ETH",
    token_ids: "ETH_USDT,ETH_USDC",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listEnabledTokens(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List supported chains
Source: https://cobo.com/developers/v2/api-references/wallets/list-supported-chains

get /wallets/chains
This operation retrieves all chains supported by a specific wallet type or subtype. 

It provides details such as the chain ID, chain symbol, and other relevant information. If you do not specify a wallet type, this operation returns a combination of chains supported by each wallet type. You can filter the result by chain IDs. The chain metadata is publicly available without any permission restrictions.

Cobo Portal currently supports over 80 blockchains and more than 3,000 tokens. In addition to this operation, you can also view the full list of supported chains [here](https://www.cobo.com/chains). We regularly update the list with new additions. If you want to request support for a specific chain or token, please [contact us](https://www.cobo.com/contact).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_supported_chains200_response import (
      ListSupportedChains200Response,
  )
  from cobo_waas2.models.wallet_subtype import WalletSubtype
  from cobo_waas2.models.wallet_type import WalletType
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_type = cobo_waas2.WalletType()
      wallet_subtype = cobo_waas2.WalletSubtype()
      chain_ids = "BTC,ETH"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List supported chains
          api_response = api_instance.list_supported_chains(
              wallet_type=wallet_type,
              wallet_subtype=wallet_subtype,
              chain_ids=chain_ids,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsApi->list_supported_chains:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->list_supported_chains: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      WalletType walletType = WalletType.fromValue("Custodial");
      WalletSubtype walletSubtype = WalletSubtype.fromValue("Asset");
      String chainIds = "BTC,ETH";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListSupportedChains200Response result =
            apiInstance.listSupportedChains(
                walletType, walletSubtype, chainIds, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listSupportedChains");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletType := coboWaas2.WalletType("Custodial")
  	walletSubtype := coboWaas2.WalletSubtype("Asset")
  	chainIds := "BTC,ETH"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListSupportedChains(ctx).
  		WalletType(walletType).
  		WalletSubtype(walletSubtype).
  		ChainIds(chainIds).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.ListSupportedChains``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListSupportedChains`: ListSupportedChains200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListSupportedChains`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const opts = {
    wallet_type: "Custodial",
    wallet_subtype: "Asset",
    chain_ids: "BTC,ETH",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listSupportedChains(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List supported tokens
Source: https://cobo.com/developers/v2/api-references/wallets/list-supported-tokens

get /wallets/tokens
This operation retrieves all tokens supported by a specific wallet type or subtype. 

It provides details such as token ID, token symbol, and other relevant information. If you do not specify a wallet type, this operation returns a combination of tokens supported by each wallet type. You can filter the result by token IDs or chain IDs. The token metadata is publicly available without any permission restrictions.

Cobo Portal currently supports over 80 blockchains and more than 3,000 tokens. In addition to this operation, you can also view the full list of supported tokens [here](https://www.cobo.com/tokens). We regularly update the list with new additions. If you want to request support for a specific chain or token, please [contact us](https://www.cobo.com/contact).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_supported_tokens200_response import (
      ListSupportedTokens200Response,
  )
  from cobo_waas2.models.wallet_subtype import WalletSubtype
  from cobo_waas2.models.wallet_type import WalletType
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_type = cobo_waas2.WalletType()
      wallet_subtype = cobo_waas2.WalletSubtype()
      chain_ids = "BTC,ETH"
      token_ids = "ETH_USDT,ETH_USDC"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List supported tokens
          api_response = api_instance.list_supported_tokens(
              wallet_type=wallet_type,
              wallet_subtype=wallet_subtype,
              chain_ids=chain_ids,
              token_ids=token_ids,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsApi->list_supported_tokens:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->list_supported_tokens: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      WalletType walletType = WalletType.fromValue("Custodial");
      WalletSubtype walletSubtype = WalletSubtype.fromValue("Asset");
      String chainIds = "BTC,ETH";
      String tokenIds = "ETH_USDT,ETH_USDC";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListSupportedTokens200Response result =
            apiInstance.listSupportedTokens(
                walletType, walletSubtype, chainIds, tokenIds, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listSupportedTokens");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletType := coboWaas2.WalletType("Custodial")
  	walletSubtype := coboWaas2.WalletSubtype("Asset")
  	chainIds := "BTC,ETH"
  	tokenIds := "ETH_USDT,ETH_USDC"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListSupportedTokens(ctx).
  		WalletType(walletType).
  		WalletSubtype(walletSubtype).
  		ChainIds(chainIds).
  		TokenIds(tokenIds).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.ListSupportedTokens``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListSupportedTokens`: ListSupportedTokens200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListSupportedTokens`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const opts = {
    wallet_type: "Custodial",
    wallet_subtype: "Asset",
    chain_ids: "BTC,ETH",
    token_ids: "ETH_USDT,ETH_USDC",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listSupportedTokens(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List token balances by address
Source: https://cobo.com/developers/v2/api-references/wallets/list-token-balances-by-address

get /wallets/{wallet_id}/addresses/{address}/tokens
The operation retrieves a list of token balances for a specified address within a wallet. 

<Note>This operation is applicable to MPC Wallets, Custodial Wallets (Web3 Wallets), and Smart Contract Wallets only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_token_balances_for_address200_response import (
      ListTokenBalancesForAddress200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
      token_ids = "ETH_USDT,ETH_USDC"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List token balances by address
          api_response = api_instance.list_token_balances_for_address(
              wallet_id,
              address,
              token_ids=token_ids,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsApi->list_token_balances_for_address:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsApi->list_token_balances_for_address: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045";
      String tokenIds = "ETH_USDT,ETH_USDC";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListTokenBalancesForAddress200Response result =
            apiInstance.listTokenBalancesForAddress(
                walletId, address, tokenIds, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listTokenBalancesForAddress");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	address := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
  	tokenIds := "ETH_USDT,ETH_USDC"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListTokenBalancesForAddress(ctx, walletId, address).
  		TokenIds(tokenIds).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsAPI.ListTokenBalancesForAddress``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTokenBalancesForAddress`: ListTokenBalancesForAddress200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListTokenBalancesForAddress`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045";
  const opts = {
    token_ids: "ETH_USDT,ETH_USDC",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listTokenBalancesForAddress(wallet_id, address, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List token balances by wallet
Source: https://cobo.com/developers/v2/api-references/wallets/list-token-balances-by-wallet

get /wallets/{wallet_id}/tokens
The operation retrieves a list of token balances within a specified wallet.

<Note>This operation is not applicable to Exchange Wallets.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_token_balances_for_address200_response import (
      ListTokenBalancesForAddress200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      token_ids = "ETH_USDT,ETH_USDC"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List token balances by wallet
          api_response = api_instance.list_token_balances_for_wallet(
              wallet_id, token_ids=token_ids, limit=limit, before=before, after=after
          )
          print("The response of WalletsApi->list_token_balances_for_wallet:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsApi->list_token_balances_for_wallet: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String tokenIds = "ETH_USDT,ETH_USDC";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListTokenBalancesForAddress200Response result =
            apiInstance.listTokenBalancesForWallet(walletId, tokenIds, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listTokenBalancesForWallet");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	tokenIds := "ETH_USDT,ETH_USDC"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListTokenBalancesForWallet(ctx, walletId).
  		TokenIds(tokenIds).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsAPI.ListTokenBalancesForWallet``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTokenBalancesForWallet`: ListTokenBalancesForAddress200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListTokenBalancesForWallet`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    token_ids: "ETH_USDT,ETH_USDC",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listTokenBalancesForWallet(wallet_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List token listing requests
Source: https://cobo.com/developers/v2/api-references/wallets/list-token-listing-requests

get /wallets/tokens/listing_requests
This operation lists all token listing requests in your organization. You can filter the results by request status.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_token_listing_requests200_response import (
      ListTokenListingRequests200Response,
  )
  from cobo_waas2.models.token_listing_request_status import TokenListingRequestStatus
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
      status = cobo_waas2.TokenListingRequestStatus()

      try:
          # List token listing requests
          api_response = api_instance.list_token_listing_requests(
              limit=limit, before=before, after=after, status=status
          )
          print("The response of WalletsApi->list_token_listing_requests:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsApi->list_token_listing_requests: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      TokenListingRequestStatus status = TokenListingRequestStatus.fromValue("Submitted");
      try {
        ListTokenListingRequests200Response result =
            apiInstance.listTokenListingRequests(limit, before, after, status);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listTokenListingRequests");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
  	status := coboWaas2.TokenListingRequestStatus("Submitted")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListTokenListingRequests(ctx).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Status(status).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsAPI.ListTokenListingRequests``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTokenListingRequests`: ListTokenListingRequests200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListTokenListingRequests`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const opts = {
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
    status: new CoboWaas2.TokenListingRequestStatus(),
  };
  apiInstance.listTokenListingRequests(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List transaction UTXOs
Source: https://cobo.com/developers/v2/api-references/wallets/list-transaction-utxos

get /wallets/{wallet_id}/transaction_utxos
The operation retrieves a list of UTXOs for a specified transaction of a wallet. You must specify the wallet, chain, and transaction hash.

<Note>This operation is applicable to MPC and Custodial Web3 Wallets.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_utxos200_response import ListUtxos200Response
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      chain_id = "ETH"
      tx_hash = "dd7e1cecf6bbde1844ee1815b780711a1e306a718bcd23cd64401b48ef88eb83"
      is_change = false
      vout_n = 0
      token_id = "ETH_USDT"
      address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List transaction UTXOs
          api_response = api_instance.list_transaction_utxos(
              wallet_id,
              chain_id,
              tx_hash,
              is_change=is_change,
              vout_n=vout_n,
              token_id=token_id,
              address=address,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsApi->list_transaction_utxos:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->list_transaction_utxos: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String chainId = "ETH";
      String txHash = "dd7e1cecf6bbde1844ee1815b780711a1e306a718bcd23cd64401b48ef88eb83";
      Boolean isChange = false;
      Integer voutN = 0;
      String tokenId = "ETH_USDT";
      String address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListUtxos200Response result =
            apiInstance.listTransactionUtxos(
                walletId,
                chainId,
                txHash,
                isChange,
                voutN,
                tokenId,
                address,
                limit,
                before,
                after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listTransactionUtxos");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	chainId := "ETH"
  	txHash := "dd7e1cecf6bbde1844ee1815b780711a1e306a718bcd23cd64401b48ef88eb83"
  	isChange := false
  	voutN := int32(0)
  	tokenId := "ETH_USDT"
  	address := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListTransactionUtxos(ctx, walletId).
  		ChainId(chainId).
  		TxHash(txHash).
  		IsChange(isChange).
  		VoutN(voutN).
  		TokenId(tokenId).
  		Address(address).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.ListTransactionUtxos``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTransactionUtxos`: ListUtxos200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListTransactionUtxos`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const chain_id = "ETH";
  const tx_hash = "dd7e1cecf6bbde1844ee1815b780711a1e306a718bcd23cd64401b48ef88eb83";
  const opts = {
    is_change: false,
    vout_n: 0,
    token_id: "ETH_USDT",
    address: "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listTransactionUtxos(wallet_id, chain_id, tx_hash, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List UTXOs
Source: https://cobo.com/developers/v2/api-references/wallets/list-utxos

get /wallets/{wallet_id}/utxos
The operation retrieves a list of **unspent** transaction outputs (UTXOs) for a specified wallet and token.

<Note>This operation returns only UTXOs that are not used by any transaction. It does not return all UTXOs.</Note>

<Info>This operation is applicable to MPC Wallets and Custodial Wallets (Web3 Wallets) only.</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_utxos200_response import ListUtxos200Response
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      token_id = "ETH_USDT"
      address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
      tx_hash = "dd7e1cecf6bbde1844ee1815b780711a1e306a718bcd23cd64401b48ef88eb83"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List UTXOs
          api_response = api_instance.list_utxos(
              wallet_id,
              token_id,
              address=address,
              tx_hash=tx_hash,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsApi->list_utxos:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->list_utxos: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String tokenId = "ETH_USDT";
      String address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045";
      String txHash = "dd7e1cecf6bbde1844ee1815b780711a1e306a718bcd23cd64401b48ef88eb83";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListUtxos200Response result =
            apiInstance.listUtxos(walletId, tokenId, address, txHash, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listUtxos");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	tokenId := "ETH_USDT"
  	address := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
  	txHash := "dd7e1cecf6bbde1844ee1815b780711a1e306a718bcd23cd64401b48ef88eb83"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListUtxos(ctx, walletId).
  		TokenId(tokenId).
  		Address(address).
  		TxHash(txHash).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.ListUtxos``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListUtxos`: ListUtxos200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListUtxos`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const token_id = "ETH_USDT";
  const opts = {
    address: "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
    tx_hash: "dd7e1cecf6bbde1844ee1815b780711a1e306a718bcd23cd64401b48ef88eb83",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listUtxos(wallet_id, token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List wallet addresses
Source: https://cobo.com/developers/v2/api-references/wallets/list-wallet-addresses

get /wallets/{wallet_id}/addresses
This operation retrieves a list of addresses within a specified wallet.
<Note>
For Web3 Wallets, Asset Wallets, and MPC Wallets, addresses created on one EVM chain automatically work on all other supported EVM chains. 

Currently, query results for EVM chain addresses differ between interfaces:

- API: Query results are limited by chain_id, so only addresses from that specific chain are returned.
- Cobo Portal: Displays addresses from all supported EVM chains, so the number of addresses may be larger than the API results.
</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_addresses200_response import ListAddresses200Response
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      chain_ids = "BTC,ETH"
      addresses = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List wallet addresses
          api_response = api_instance.list_addresses(
              wallet_id,
              chain_ids=chain_ids,
              addresses=addresses,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of WalletsApi->list_addresses:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->list_addresses: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String chainIds = "BTC,ETH";
      String addresses =
          "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListAddresses200Response result =
            apiInstance.listAddresses(walletId, chainIds, addresses, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#listAddresses");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	chainIds := "BTC,ETH"
  	addresses := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.ListAddresses(ctx, walletId).
  		ChainIds(chainIds).
  		Addresses(addresses).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.ListAddresses``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListAddresses`: ListAddresses200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListAddresses`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    chain_ids: "BTC,ETH",
    addresses:
      "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listAddresses(wallet_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Lock UTXOs
Source: https://cobo.com/developers/v2/api-references/wallets/lock-utxos

post /wallets/{wallet_id}/utxos/lock
This operation locks the UTXOs with specified transaction hashes. Locked UTXOs cannot be transferred until unlocked.

<Note>This operation is applicable to MPC Wallets and Custodial Wallets (Web3 Wallets) only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.lock_utxos201_response import LockUtxos201Response
  from cobo_waas2.models.lock_utxos_request import LockUtxosRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      lock_utxos_request = cobo_waas2.LockUtxosRequest(
          utxos=[
              cobo_waas2.LockUtxosRequestUtxosInner(
                  token_id="BTC",
                  tx_hash="9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb",
                  vout_n=0,
              )
          ]
      )

      try:
          # Lock UTXOs
          api_response = api_instance.lock_utxos(
              wallet_id, lock_utxos_request=lock_utxos_request
          )
          print("The response of WalletsApi->lock_utxos:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->lock_utxos: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      LockUtxosRequest lockUtxosRequest =
          new LockUtxosRequest()
              .utxos(
                  Arrays.asList(
                      new LockUtxosRequestUtxosInner()
                          .tokenId("BTC")
                          .txHash("9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb")
                          .voutN(0)));
      try {
        LockUtxos201Response result = apiInstance.lockUtxos(walletId, lockUtxosRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#lockUtxos");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	lockUtxosRequest := *coboWaas2.NewLockUtxosRequest([]coboWaas2.LockUtxosRequestUtxosInner{*coboWaas2.NewLockUtxosRequestUtxosInner("BTC", "9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb", int32(0))})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.LockUtxos(ctx, walletId).
  		LockUtxosRequest(lockUtxosRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.LockUtxos``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `LockUtxos`: LockUtxos201Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.LockUtxos`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    LockUtxosRequest: CoboWaas2.LockUtxosRequest.constructFromObject({
      utxos: [
        {
          token_id: "BTC",
          tx_hash:
            "9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb",
          vout_n: 0,
        },
      ],
    }),
  };
  apiInstance.lockUtxos(wallet_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Refresh address balances by token
Source: https://cobo.com/developers/v2/api-references/wallets/refresh-address-balances-by-token

put /wallets/{wallet_id}/tokens/{token_id}/refresh_address_balances
This operation refreshes the balances of specified addresses for a given token within a wallet.

The successful return of the request only means that the refresh request has been submitted.

<Note>This operation is applicable to MPC Wallets only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.refresh_address_balances_by_token200_response import (
      RefreshAddressBalancesByToken200Response,
  )
  from cobo_waas2.models.refresh_address_balances_by_token_request import (
      RefreshAddressBalancesByTokenRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      token_id = "ETH_USDT"
      refresh_address_balances_by_token_request = (
          cobo_waas2.RefreshAddressBalancesByTokenRequest(
              addresses=["3HYV6ta67197syD1ZVFganpmL2wLz4RyoC"]
          )
      )

      try:
          # Refresh address balances by token
          api_response = api_instance.refresh_address_balances_by_token(
              wallet_id,
              token_id,
              refresh_address_balances_by_token_request=refresh_address_balances_by_token_request,
          )
          print("The response of WalletsApi->refresh_address_balances_by_token:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsApi->refresh_address_balances_by_token: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String tokenId = "ETH_USDT";
      RefreshAddressBalancesByTokenRequest refreshAddressBalancesByTokenRequest =
          new RefreshAddressBalancesByTokenRequest()
              .addresses(Arrays.asList("3HYV6ta67197syD1ZVFganpmL2wLz4RyoC"));
      try {
        RefreshAddressBalancesByToken200Response result =
            apiInstance.refreshAddressBalancesByToken(
                walletId, tokenId, refreshAddressBalancesByTokenRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#refreshAddressBalancesByToken");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	tokenId := "ETH_USDT"
  	refreshAddressBalancesByTokenRequest := *coboWaas2.NewRefreshAddressBalancesByTokenRequest([]string{"3HYV6ta67197syD1ZVFganpmL2wLz4RyoC"})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.RefreshAddressBalancesByToken(ctx, walletId, tokenId).
  		RefreshAddressBalancesByTokenRequest(refreshAddressBalancesByTokenRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsAPI.RefreshAddressBalancesByToken``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `RefreshAddressBalancesByToken`: RefreshAddressBalancesByToken200Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.RefreshAddressBalancesByToken`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const token_id = "ETH_USDT";
  const opts = {
    RefreshAddressBalancesByTokenRequest:
      CoboWaas2.RefreshAddressBalancesByTokenRequest.constructFromObject({
        addresses: ["3HYV6ta67197syD1ZVFganpmL2wLz4RyoC"],
      }),
  };
  apiInstance.refreshAddressBalancesByToken(wallet_id, token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Unlock UTXOs
Source: https://cobo.com/developers/v2/api-references/wallets/unlock-utxos

post /wallets/{wallet_id}/utxos/unlock
This operation unlocks the UTXOs with specified transaction hashes. Locked UTXOs cannot be transferred until unlocked.   
<Note>This operation is applicable to MPC Wallets and Custodial Wallets (Web3 Wallets) only.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.lock_utxos201_response import LockUtxos201Response
  from cobo_waas2.models.lock_utxos_request import LockUtxosRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      lock_utxos_request = cobo_waas2.LockUtxosRequest(
          utxos=[
              cobo_waas2.LockUtxosRequestUtxosInner(
                  token_id="BTC",
                  tx_hash="9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb",
                  vout_n=0,
              )
          ]
      )

      try:
          # Unlock UTXOs
          api_response = api_instance.unlock_utxos(
              wallet_id, lock_utxos_request=lock_utxos_request
          )
          print("The response of WalletsApi->unlock_utxos:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->unlock_utxos: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      LockUtxosRequest lockUtxosRequest =
          new LockUtxosRequest()
              .utxos(
                  Arrays.asList(
                      new LockUtxosRequestUtxosInner()
                          .tokenId("BTC")
                          .txHash("9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb")
                          .voutN(0)));
      try {
        LockUtxos201Response result = apiInstance.unlockUtxos(walletId, lockUtxosRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#unlockUtxos");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	lockUtxosRequest := *coboWaas2.NewLockUtxosRequest([]coboWaas2.LockUtxosRequestUtxosInner{*coboWaas2.NewLockUtxosRequestUtxosInner("BTC", "9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb", int32(0))})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.UnlockUtxos(ctx, walletId).
  		LockUtxosRequest(lockUtxosRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.UnlockUtxos``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UnlockUtxos`: LockUtxos201Response
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.UnlockUtxos`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    LockUtxosRequest: CoboWaas2.LockUtxosRequest.constructFromObject({
      utxos: [
        {
          token_id: "BTC",
          tx_hash:
            "9bdf8e7ae03c237e115f09543fbdb40f8efa600106e78b67ce4d5adfadda2dbb",
          vout_n: 0,
        },
      ],
    }),
  };
  apiInstance.unlockUtxos(wallet_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Update wallet
Source: https://cobo.com/developers/v2/api-references/wallets/update-wallet

put /wallets/{wallet_id}
This operation updates the information of a specified wallet.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.update_wallet_params import UpdateWalletParams
  from cobo_waas2.models.wallet_info import WalletInfo
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      update_wallet_params = cobo_waas2.UpdateWalletParams(
          cobo_waas2.UpdateCustodialWalletParams(wallet_type="Custodial")
      )

      try:
          # Update wallet
          api_response = api_instance.update_wallet_by_id(
              wallet_id, update_wallet_params=update_wallet_params
          )
          print("The response of WalletsApi->update_wallet_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling WalletsApi->update_wallet_by_id: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsApi apiInstance = new WalletsApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      UpdateWalletParams updateWalletParams =
          new UpdateWalletParams(new UpdateCustodialWalletParams().walletType(WalletType.CUSTODIAL));
      try {
        WalletInfo result = apiInstance.updateWalletById(walletId, updateWalletParams);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsApi#updateWalletById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	updateWalletParams := coboWaas2.UpdateWalletParams{
  		UpdateCustodialWalletParams: coboWaas2.NewUpdateCustodialWalletParams(
  			coboWaas2.WalletType("Custodial"),
  		),
  	}

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsAPI.UpdateWalletById(ctx, walletId).
  		UpdateWalletParams(updateWalletParams).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.UpdateWalletById``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UpdateWalletById`: WalletInfo
  	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.UpdateWalletById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    UpdateWalletParams: CoboWaas2.UpdateWalletParams.constructFromObject({
      wallet_type: "Custodial",
    }),
  };
  apiInstance.updateWalletById(wallet_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Integrate Custodial Wallets (Asset Wallets)
Source: https://cobo.com/developers/v2/guides/custodial-wallets/get-started-asset-wallets



<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

After you have familiarized yourself with Custodial Wallets through the [Cobo Portal quick start guide](https://manuals.cobo.com/en/portal/quick-start-guide-custodial-wallets), this guide will help you seamlessly integrate Custodial Wallet (Asset Wallets) functionality into your application using the WaaS 2.0 API.

Following this guide, you'll learn how to:

1. Create a wallet
2. Generate a deposit address within the wallet
3. Deposit tokens into the wallet and track the transaction status
4. Withdraw tokens from the wallet
5. Query wallet balances
6. Automatically sweep funds to a designated address

<Note>This guide uses the [development environment](/developers/v2/guides/overview/environments) in all its code samples. It is recommended that you use the development environment to test your new features first before deploying them to the production environment. </Note>

## Prerequisites

* Follow the instructions in [Send your first request](/developers/v2/guides/get-started/get-started-with-waas) to set up your account and send your first API request to the WaaS 2.0 service.
* If you choose to use a WaaS SDK instead of manually writing the API requests, refer to the SDK guide corresponding to the programming language of your choice ([Python](/developers/v2/developer-tools/quickstart-python), [Java](/developers/v2/developer-tools/quickstart-java), [Go](/developers/v2/developer-tools/quickstart-go), [JavaScript](/developers/v2/developer-tools/quickstart-javascript)) to integrate the SDK into your project.

## 1. Create a wallet

To create an Asset Wallet, call the [Create wallet](/developers/v2/api-references/wallets/create-wallet) operation and specify the properties in the request body as follows:

* `wallet_type`: `Custodial`.
* `wallet_subtype`: `Asset`.

Upon successful completion of the request, the response will include the wallet ID, which is the unique identifier of the wallet you have just created. Store this wallet ID as you will need it for subsequent steps.

<Accordion title="Sample code in Python">
  ```python theme={null}
  import json

  import cobo_waas2
  from cobo_waas2 import (
     WalletType,
     WalletSubtype,
     CreateCustodialWalletParams,
     CreateWalletParams,
  )

  configuration = cobo_waas2.Configuration(
     # Replace `<YOUR_API_SECRET>` with your API secret
     api_private_key="<YOUR_API_SECRET>",
     # Use the development environment
     host="https://api.dev.cobo.com/v2"
  )

  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
     # Create an instance of the API class
     wallet_api_instance = cobo_waas2.WalletsApi(api_client)
     try:
         # Create an Asset Wallet
         api_response = wallet_api_instance.create_wallet(
             CreateWalletParams(
                 actual_instance=CreateCustodialWalletParams(
                     name="Asset Example Wallet Demo(Python)",
                     wallet_type=WalletType.CUSTODIAL,
                     wallet_subtype=WalletSubtype.ASSET,
                 )
             )
         )
         print("The response of WalletsApi->create_wallet:")
         print(json.dumps(api_response.to_dict(), indent=2))

     except Exception as e:
         print("Exception when calling WalletsApi->create_wallet, %s\n", e)

  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class CreateWalletExample {
     public static void main(String[] args) {
         ApiClient defaultClient = Configuration.getDefaultApiClient();
         // Use the development environment
         defaultClient.setEnv(Env.DEV);
         // Replace `<YOUR_API_SECRET>` with your API secret
         defaultClient.setPrivKey("<YOUR_API_SECRET>");
         WalletsApi apiInstance = new WalletsApi();
         try {
             CreateCustodialWalletParams params = new CreateCustodialWalletParams()
                     .name("Asset Example Wallet Demo(Java)")
                     .walletType(WalletType.CUSTODIAL)
                     .walletSubtype(WalletSubtype.ASSET);
             // Create an Asset Wallet
             CreatedWalletInfo result = apiInstance.createWallet(new CreateWalletParams(params));
             System.out.println(result);
         } catch (ApiException e) {
             System.err.println("Exception when calling WalletsApi#createWallet");
             System.err.println("Status code: " + e.getCode());
             System.err.println("Reason: " + e.getResponseBody());
             System.err.println("Response headers: " + e.getResponseHeaders());
             e.printStackTrace();
         }
     }
  }
  ```
</Accordion>

## 2. Generate deposit addresses

After setting up a wallet, you now need to generate deposit addresses within the wallet to receive tokens. To generate deposit addresses within the Asset Wallet you have just created, call the [Create addresses in wallet](/developers/v2/api-references/wallets/create-addresses-in-wallet) operation and specify the parameters and properties as follows:

* Path:
  * `wallet_id`: The ID of the wallet you have just created.
* Request body:
  * `chain_id`: The ID of the blockchain.
  * `count`: Use this parameter to specify the number of addresses you want to create.

Upon successful completion of the request, the response will include the addresses you have just created. You can now proceed to deposit tokens into these addresses.

<Accordion title="Sample code in Python">
  ```python theme={null}
  import json

  import cobo_waas2
  from cobo_waas2 import (
     CreateAddressRequest,
     AddressEncoding,
  )

  configuration = cobo_waas2.Configuration(
     # Replace `<YOUR_API_SECRET>` with your API secret
     api_private_key="<YOUR_API_SECRET>",
     # Use the development environment
     host="https://api.dev.cobo.com/v2"
  )

  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
     # Create an instance of the API class
     wallet_api_instance = cobo_waas2.WalletsApi(api_client)
     try:
         # Generate two addresses on the Bitcoin testnet3 (XTN) chain using P2TR encoding
         api_response = wallet_api_instance.create_address(
             wallet_id="<Your Wallet ID>",
             create_address_request=CreateAddressRequest(
                 chain_id="XTN", count=2, encoding=AddressEncoding.ENCODING_P2_TR
             ),
         )
         print("The response of WalletsApi->create_address:")
         for address_info in api_response:
             print(json.dumps(address_info.to_dict(), indent=2))

     except Exception as e:
         print("Exception when calling WalletsApi->create_address, %s\n", e)
  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.AddressEncoding;
  import com.cobo.waas2.model.AddressInfo;
  import com.cobo.waas2.model.CreateAddressRequest;

  import java.util.List;
  import java.util.UUID;

  public class CreateAddressExample {
     public static void main(String[] args) {
         ApiClient defaultClient = Configuration.getDefaultApiClient();
         // Use the development environment
         defaultClient.setEnv(Env.DEV);
         // Replace `<YOUR_API_SECRET>` with your API secret
         defaultClient.setPrivKey("<YOUR_API_SECRET>");
         WalletsApi apiInstance = new WalletsApi();
         try {
             UUID wallet_id = UUID.fromString("<YOUR_WALLET_ID>");
             CreateAddressRequest params = new CreateAddressRequest()
                     .chainId("XTN")
                     .count(2)
                     .encoding(AddressEncoding.BECH32);
             // Generate two addresses on the Bitcoin testnet3 (XTN) chain using P2TR encoding
             List<AddressInfo> result = apiInstance.createAddress(wallet_id, params);
             for (AddressInfo addressInfo : result)
                 System.out.println(addressInfo);
         } catch (ApiException e) {
             System.err.println("Exception when calling WalletsApi#createAddress");
             System.err.println("Status code: " + e.getCode());
             System.err.println("Reason: " + e.getResponseBody());
             System.err.println("Response headers: " + e.getResponseHeaders());
             e.printStackTrace();
         }
     }
  }
  ```
</Accordion>

## 3. Process deposit

After depositing tokens to the addresses you have generated, you can track the status of your deposit using one of the following two options. Compared with using API to query the transaction status, webhooks can give you real-time notifications and are thus the recommended option.

### Option 1: Use webhooks for real-time notifications

Webhook is an essential mechanism for the WaaS service to communicate with your application. After you register a webhook endpoint on Cobo Portal, the WaaS service sends push messages to the designated URL when an event occurs.

To learn how to set up a webhook endpoint and register it on Cobo Portal, refer to [Introduction to webhooks and callbacks](/developers/v2/guides/webhooks-callbacks/introduction).

To track the status of your deposit, you can subscribe to the following webhook event types:

* wallets.transaction.created
* wallets.transaction.updated
* wallets.transaction.succeeded
* wallets.transaction.failed

To learn the trigger condition and data structure of each event type, refer to [Webhook event types and data types](/developers/v2/guides/webhooks-callbacks/webhook-event-type).

### Option 2: Get transaction status by API call

To query the status of a deposit transaction, call the [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation and set the query parameters as follows:

* `types`: `Deposit`.
* `statuses`: `Confirming,Completed`. If you are depositing from an external address, you will be able to query the transaction details when the transaction is waiting for the required number of confirmations or when it is successfully completed.
* `wallet_ids`: The ID of the wallet you have created in the first step.

<Accordion title="Sample code in Python">
  ```python theme={null}
  import json
  import uuid

  import cobo_waas2
  from cobo_waas2 import (
     CreateAddressRequest,
     AddressEncoding,
     TransferParams,
     TransferSource,
     CustodialTransferSource,
     WalletSubtype,
     TransferDestination, AddressTransferDestination, TransferDestinationType, AddressTransferDestinationAccountOutput,
  )

  configuration = cobo_waas2.Configuration(
     # Replace `<YOUR_API_SECRET>` with your API secret
     api_private_key="<YOUR_API_SECRET>",
     # Use the development environment
     host="https://api.dev.cobo.com/v2"
  )

  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
     # Create an instance of the API class
     transaction_api_instance = cobo_waas2.TransactionsApi(api_client)
     try:
         # List deposit transactions
         api_response = transaction_api_instance.list_transactions(
             types="Deposit",
             statuses="Confirming,Completed",
             wallet_ids="<YOUR_WALLET_ID>"
         )
         print("The response of TransactionsApi->list_transactions:")
         print(json.dumps(api_response.to_dict(), indent=2))

     except Exception as e:
         print("Exception when calling TransactionsApi->list_transactions, %s\n", e)
  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.ListTransactions200Response;

  import java.util.UUID;

  public class ListTransactionsExample {
     public static void main(String[] args) {
         ApiClient defaultClient = Configuration.getDefaultApiClient();
         // Use the development environment
         defaultClient.setEnv(Env.DEV);
         // Replace `<YOUR_API_SECRET>` with your API secret
         defaultClient.setPrivKey("<YOUR_API_SECRET>");
         TransactionsApi apiInstance = new TransactionsApi();
         try {
             String requestId = null;
             String coboIds = null;
             String transactionIds = null;
             String transactionHashes = "";
             String types = "Deposit";
             String statuses = "Confirming,Completed";
             String walletIds = "<YOUR_WALLET_ID>";
             String chainIds = null;
             String tokenIds = null;
             String assetIds = null;
             UUID vaultId = null;
             UUID projectId = null;
             Long minCreatedTimestamp = null;
             Long maxCreatedTimestamp = null;
             Integer limit = 50;
             String before = null;
             String after = null;

             // List deposit transactions
             ListTransactions200Response result = apiInstance.listTransactions(
                     requestId, coboIds, transactionIds, transactionHashes, types, statuses, walletIds, chainIds,
                     tokenIds, assetIds, vaultId, projectId, minCreatedTimestamp, maxCreatedTimestamp, limit, before, after);
             System.out.println(result);
         } catch (ApiException e) {
             System.err.println("Exception when calling WalletsApi#createAddress");
             System.err.println("Status code: " + e.getCode());
             System.err.println("Reason: " + e.getResponseBody());
             System.err.println("Response headers: " + e.getResponseHeaders());
             e.printStackTrace();
         }
     }
  }
  ```
</Accordion>

## Deposit prerequisites

Before you deposit tokens, make sure the chain is activated for your organization and the token is listed and enabled for deposits. A token accepts deposits only when its `can_deposit` property is `true`. Deposits made to a token that is not enabled (`can_deposit` is `false`, meaning deposits are currently suspended) may not be detected or credited automatically, so confirm this property before you send funds.

**Check whether a token accepts deposits**

Call the [List supported tokens](/developers/v2/api-references/wallets/list-supported-tokens) operation and set the query parameter `token_ids` to the token you want to check (for example, `ETH_USDT`). In the response, read the `can_deposit` field of the token:

* `true`: Deposits are enabled. You can deposit to this token.
* `false`: Deposits are currently suspended. Do not send funds.

To check a single token, you can also call [Get token information](/developers/v2/api-references/wallets/get-token-information) with the `token_id` path parameter. Both operations accept the optional query parameters `wallet_type`, `wallet_subtype`, and `chain_ids` to narrow the results.

**Check the status of a deposit you already sent**

If you have already sent a deposit to a token that was not enabled at the time, do not send further funds to the same address. Instead, confirm the current status of the transfer by calling the [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation with the following query parameters:

* `types`: `Deposit`.
* `token_ids`: The token you deposited, for example `ETH_USDT`.
* `wallet_ids`: The ID of your wallet.
* `transaction_hash` (optional): The on-chain transaction hash, to locate a specific transfer.

Read the `status` field of each returned transaction to determine whether the deposit has been recorded. For sample code that calls this operation, see [Option 2: Get transaction status by API call](#option-2-get-transaction-status-by-api-call).

## Memo and tag requirements

Some chains require a memo or tag in addition to the deposit address so that the deposit can be routed to the correct account, such as XRP, XLM, EOS, ATOM, TON, IOST, BNB Chain, and Hedera. A deposit sent to one of these chains without the required memo or tag, or with an incorrect memo or tag, will fail to match the deposit address and will not be credited automatically. If a deposit on a memo-required chain does not appear in your transaction list, contact [help@cobo.com](mailto:help@cobo.com) for assistance.

**Check whether a chain requires a memo or tag**

Call the [List supported chains](/developers/v2/api-references/wallets/list-supported-chains) operation (or [List enabled chains](/developers/v2/api-references/wallets/list-enabled-chains) for the chains enabled for your organization) and read the `require_memo` field of the chain:

* `true`: The chain requires a memo or tag for every deposit.
* `false`: No memo or tag is required.

To check a single chain, call [Get chain information](/developers/v2/api-references/wallets/get-chain-information) with the `chain_id` path parameter.

**Get the memo or tag for a deposit address**

The memo or tag is bound to the deposit address. When you generate an address on a memo-required chain, the address response includes a `memo` field. Retrieve it from the response of [Create addresses in wallet](/developers/v2/api-references/wallets/create-addresses-in-wallet), or look it up later with [List wallet addresses](/developers/v2/api-references/wallets/list-wallet-addresses). When you deposit, provide both the address and its `memo` value from this response, and include the exact memo or tag with every transfer.

**Confirm a deposit on a memo-required chain**

To check whether a deposit to a memo-required chain has been credited, call the [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation with `types` set to `Deposit` and `wallet_ids` set to your wallet ID, then read the `status` field of each returned transaction.

## Internal and contract-triggered transactions

The deposit detection mechanism tracks standard top-level transfers to your deposit addresses. Transfers that are not top-level — such as internal (trace) transfers produced by a contract call, or token movements emitted by a smart contract rather than sent directly to your address — may not be detected or credited automatically. This applies to several chains.

If you expect a deposit from this type of transfer and it does not appear, first verify that the transaction was completed on-chain using the relevant blockchain explorer, then use the [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation to check whether it has been recorded by Cobo. If no record is found, contact [help@cobo.com](mailto:help@cobo.com) for assistance.

## Deposit troubleshooting

### How do I re-check a deposit if I missed its webhook notification?

Webhook notifications can be missed if your endpoint was temporarily unavailable. You do not need to wait for a new notification to confirm a deposit. Query the current state directly with the [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation, or retrieve a single transfer with the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operation. Make sure your webhook endpoint returns a success status code so that future events are delivered reliably; see [Introduction to webhooks and callbacks](/developers/v2/guides/webhooks-callbacks/introduction).

### What happens to deposits made before a token is listed?

Deposits sent before a token is listed and enabled for deposits may not be detected or credited at the time of the transfer. Before depositing, confirm that the token is enabled as described in [Deposit prerequisites](#deposit-prerequisites). To check whether such a deposit has since been recorded, use the [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation. If the transaction does not appear, there is no automatic recovery for pre-listing deposits. Contact [help@cobo.com](mailto:help@cobo.com) for assistance.

## 4. Withdraw tokens

Now that you have tokens in your wallet, it's time to try withdrawing them.

### Set up a callback endpoint

To enhance the security of your transactions, it is highly recommended that you set up a callback endpoint to receive and approve withdrawal requests. Once you initiate a withdrawal using the WaaS 2.0 API, the callback endpoint will receive a callback message containing the transaction details. The transaction will proceed only if you approve the withdrawal request.

To learn how to set up a callback endpoint and register it on Cobo Portal, refer to [Introduction to webhooks and callbacks](/developers/v2/guides/webhooks-callbacks/introduction).

### Withdraw tokens

To withdraw tokens from the Asset Wallet, call the [Transfer token](/developers/v2/api-references/transactions/transfer-token) operation and set the properties in the request body as follows:

* `request_id`: Your request ID.
* `source.source_type`: `Asset`.
* `source.wallet_id`: The ID of the wallet you have just created.
* `token_id`: The ID of the token you want to withdraw.
* `destination.destination_type`: `Address`.
* `destination.account_output`: The receiving address and memo (if applicable), and the amount you want to withdraw.
* `category_names`: The custom category for you to identify your transactions.
* `description`: The description of the transfer.

<Accordion title="Sample code in Python">
  ```python theme={null}
  import json
  import uuid

  import cobo_waas2
  from cobo_waas2 import (
     CreateAddressRequest,
     AddressEncoding,
     TransferParams,
     TransferSource,
     CustodialTransferSource,
     WalletSubtype,
     TransferDestination, AddressTransferDestination, TransferDestinationType, AddressTransferDestinationAccountOutput,
  )

  configuration = cobo_waas2.Configuration(
     # Replace `<YOUR_API_SECRET>` with your API secret
     api_private_key="<YOUR_API_SECRET>",
     # Use the development environment
     host="https://api.dev.cobo.com/v2"
  )

  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
     # Create an instance of the API class
     transaction_api_instance = cobo_waas2.TransactionsApi(api_client)
     try:
         # Transfer Bitcoin testnet3(XTN) token from the wallet
         api_response = transaction_api_instance.create_transfer_transaction(
             transfer_params=TransferParams(
                 request_id=str(uuid.uuid4()),
                 source=TransferSource(
                     actual_instance=CustodialTransferSource(
                         source_type=WalletSubtype.ASSET,
                         wallet_id="<YOUR_WALLET ID>",
                     )
                 ),
                 token_id="XTN",
                 destination=TransferDestination(
                     actual_instance=AddressTransferDestination(
                         destination_type=TransferDestinationType.ADDRESS,
                         account_output=AddressTransferDestinationAccountOutput(
                             address="<TARGET_ADDRESS>",
                             amount="<TRANSFER_AMOUNT>"
                         )
                     )
                 ),
                 category_names=["<CATEGORY_NAME>"],
                 description="<DESCRIPTION>",
             )
         )
         print("The response of TransactionsApi->create_transfer_transaction:")
         print(json.dumps(api_response.to_dict(), indent=2))

     except Exception as e:
         print("Exception when calling TransactionsApi->create_transfer_transaction, %s\n", e)
  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  import java.util.ArrayList;
  import java.util.List;
  import java.util.UUID;

  public class TransferExample {
     public static void main(String[] args) {
         ApiClient defaultClient = Configuration.getDefaultApiClient();
         // Use the development environment
         defaultClient.setEnv(Env.DEV);
         // Replace `<YOUR_API_SECRET>` with your API secret
         defaultClient.setPrivKey("<YOUR_API_SECRET>");
         TransactionsApi apiInstance = new TransactionsApi();
         try {
             UUID walletId = UUID.fromString("<YOUR_WALLET_ID>");

             TransferParams params = new TransferParams();
             params.setRequestId("Demo" + UUID.randomUUID());

             CustodialTransferSource custodialTransferSource = new CustodialTransferSource().sourceType(WalletSubtype.ASSET).walletId(walletId
  );
             params.setSource(new TransferSource(custodialTransferSource));

             params.setTokenId("XTN");
             AddressTransferDestination addressTransferDestination = new AddressTransferDestination()
                     .destinationType(TransferDestinationType.ADDRESS)
                     .accountOutput(new AddressTransferDestinationAccountOutput()
                             .address("<TARGET_ADDRESS>")
                             .amount("<TRANSFER_AMOUNT>"));
             params.setDestination(new TransferDestination(addressTransferDestination));

             List<String> categoryNames = new ArrayList<>();
             categoryNames.add("<CATEGORY_NAME>");
             params.categoryNames(categoryNames).description("<DESCRIPTION>");

             // Transfer Bitcoin testnet3(XTN) token from the wallet
             CreateTransferTransaction201Response result = apiInstance.createTransferTransaction(params);
             System.out.println(result);
         } catch (ApiException e) {
             System.err.println("Exception when calling TransactionsApi#createTransferTransaction");
             System.err.println("Status code: " + e.getCode());
             System.err.println("Reason: " + e.getResponseBody());
             System.err.println("Response headers: " + e.getResponseHeaders());
             e.printStackTrace();
         }
     }
  }
  ```
</Accordion>

The response of the withdrawal request is as follows. Record the transaction ID as you will use it in the following steps.

```json theme={null}
{
   "request_id": "<YOUR_REQUEST_ID>",
   "transaction_id": "<THE_GENERATED_TRANSACTION_ID>",
   "status": "Submitted"
}
```

### Confirm the withdrawal

If you have set up a callback endpoint, after you initiate the withdrawal transaction, your callback endpoint will receive a message containing the transaction details. Check if the transaction meets expectations, and respond with a success status code (200 or 201) and a response body of `ok` to approve the transaction. To learn more about handling a callback message, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).

### Monitor the withdrawal status

In addition to webhook events, you can also call the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operation to query the status of the transaction. Set the path parameter `transaction_id` to the transaction ID returned in the response of the previous withdrawal request.

<Accordion title="Sample code in Python">
  ```python theme={null}
  import json
  import uuid

  import cobo_waas2
  from cobo_waas2 import (
     CreateAddressRequest,
     AddressEncoding,
     TransferParams,
     TransferSource,
     CustodialTransferSource,
     WalletSubtype,
     TransferDestination, AddressTransferDestination, TransferDestinationType, AddressTransferDestinationAccountOutput,
  )

  configuration = cobo_waas2.Configuration(
     # Replace `<YOUR_API_SECRET>` with your API secret
     api_private_key="<YOUR_API_SECRET>",
     # Use the development environment
     host="https://api.dev.cobo.com/v2"
  )

  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
     # Create an instance of the API class
     transaction_api_instance = cobo_waas2.TransactionsApi(api_client)
     try:
         # Get transaction by ID
         api_response = transaction_api_instance.get_transaction_by_id(
             transaction_id="<YOUR_TRANSACTION_ID>"
         )
         print("The response of TransactionsApi->get_transaction_by_id:")
         print(json.dumps(api_response.to_dict(), indent=2))

     except Exception as e:
         print("Exception when calling TransactionsApi->get_transaction_by_id, %s\n", e)
  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.TransactionDetail;

  import java.util.UUID;

  public class GetTransactionExample {
     public static void main(String[] args) {
         ApiClient defaultClient = Configuration.getDefaultApiClient();
         // Use the development environment
         defaultClient.setEnv(Env.DEV);
         // Replace `<YOUR_API_SECRET>` with your API secret
         defaultClient.setPrivKey("<YOUR_API_SECRET>");
         TransactionsApi apiInstance = new TransactionsApi();
         try {
             UUID transactionId = UUID.fromString("<YOUR_TRANSACTION_ID>");
             
             // Get transaction by ID
             TransactionDetail result = apiInstance.getTransactionById(transactionId);
             System.out.println(result);
         } catch (ApiException e) {
             System.err.println("Exception when calling TransactionsApi#getTransactionById");
             System.err.println("Status code: " + e.getCode());
             System.err.println("Reason: " + e.getResponseBody());
             System.err.println("Response headers: " + e.getResponseHeaders());
             e.printStackTrace();
         }
     }
  }
  ```
</Accordion>

## 5. Query wallet balances

After successfully withdrawing tokens from your wallet, you can call [List token balances by wallet](/developers/v2/api-references/wallets/list-token-balances-by-wallet) to query the wallet balances. Specify the path and query parameters as follows:

* `wallet_id`: The ID of the wallet you have just created.
* `token_ids`: You can leave it empty to query the balances of all tokens, or set it to the specific token you want to query.

<Accordion title="Sample code in Python">
  ```python theme={null}
  import json

  import cobo_waas2
  from cobo_waas2 import (
     WalletType,
     WalletSubtype,
  )

  configuration = cobo_waas2.Configuration(
     # Replace `<YOUR_API_SECRET>` with your API secret
     api_private_key="<YOUR_API_SECRET>",
     # Use the development environment
     host="https://api.dev.cobo.com/v2"
  )

  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
     # Create an instance of the API class
     wallet_api_instance = cobo_waas2.WalletsApi(api_client)
     try:
         # Query token balances
         api_response = wallet_api_instance.list_token_balances_for_wallet(
             wallet_id="<YOUR_WALLET_ID>",
         )
         print(f"The response of WalletsApi->list_token_balances_for_wallet:")
         print(json.dumps(api_response.to_dict(), indent=2))

     except Exception as e:
         print("Exception when calling WalletsApi->list_token_balances_for_wallet, %s\n", e)
  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.ListTokenBalancesForAddress200Response;

  import java.util.UUID;

  public class ListTokenBalancesExample {
      public static void main(String[] args) {
          ApiClient defaultClient = Configuration.getDefaultApiClient();
          // Use the development environment
          defaultClient.setEnv(Env.DEV);
          // Replace `<YOUR_API_SECRET>` with your API secret
          defaultClient.setPrivKey("<YOUR_API_SECRET>");
          WalletsApi apiInstance = new WalletsApi();
          try {
              UUID wallet_id = UUID.fromString("<YOUR_WALLET_ID>");
              String tokenIds = null;
              Integer limit = 50;
              String before = null;
              String after = null;
              // Query token balances
              ListTokenBalancesForAddress200Response result = apiInstance.listTokenBalancesForWallet(wallet_id, tokenIds, limit, before, after);
              System.out.println(result);
          } catch (ApiException e) {
              System.err.println("Exception when calling WalletsApi#listTokenBalancesForWallet");
              System.err.println("Status code: " + e.getCode());
              System.err.println("Reason: " + e.getResponseBody());
              System.err.println("Response headers: " + e.getResponseHeaders());
              e.printStackTrace();
          }
      }
  }
  ```
</Accordion>

## 6. Sweep funds automatically (auto-sweep)

Auto-sweep automatically consolidates tokens from your deposit addresses into a designated sweep-to address, so that you do not need to move funds out of each deposit address manually. To create an auto-sweep task, call the [Create auto-sweep task](/developers/v2/api-references/autosweep/create-auto-sweep-task) operation and specify the following:

* `wallet_id`: The ID of the wallet you created.
* `token_id`: The ID of the token to sweep.
* `min_balance_threshold`: (Optional) The minimum token balance an address must hold to be swept. Addresses holding less than this value are skipped, which lets you filter out dust. There is no per-address blocklist; use `min_balance_threshold` to control the minimum sweep amount.

<Note>
  A sweep moves tokens out of a deposit address, which requires native chain coin to pay for gas. Make sure that gas is available either in the source deposit address or through a configured Fee Station or Auto Fueling. Reaching the deposit threshold alone does not complete a sweep: if no gas is available, the sweep cannot be broadcast. When a sweep cannot proceed, the reason is reported in the `failed_reasons` array returned by the task details.
</Note>

### Retrieve the swept transactions

The Create auto-sweep task operation returns immediately with a `task_id`. At this point the task `status` is `Submitted` and the `transaction_ids` array is empty. This is expected and does not indicate a failure.

The task transitions to `TransactionCreated` once it triggers one or more sweep transactions, at which point `transaction_ids` is populated. To retrieve the transaction IDs, poll the [Get auto-sweep task details](/developers/v2/api-references/autosweep/get-auto-sweep-task-details) operation with your `task_id` until `status` becomes `TransactionCreated`.

### Timing and lifecycle

Auto-sweep is poll-based rather than instant. A sweep is initiated shortly after its trigger condition is met, so a short delay between the deposit and the sweep transaction is normal. Tasks that cannot proceed do not stay pending indefinitely: a task that remains without gas or without a signature is automatically cancelled after a timeout, and the affected funds remain in the source address so that you can sweep them again later.

<Info>For EVM-compatible chains (such as Ethereum and BNB Smart Chain), the same address is used across all EVM chains. As a result, when you list sweep-to addresses with [List sweep-to addresses](/developers/v2/api-references/autosweep/list-sweep-to-addresses), only one address entry (shown under Ethereum) is returned for all EVM-compatible chains. Do not expect a separate entry for each EVM chain.</Info>


# Send your first request
Source: https://cobo.com/developers/v2/guides/get-started/get-started-with-waas

Use the WaaS 2.0 API: set up account, generate API key, authenticate requests, and send API requests.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## Overview

This guide explains how to get started with using the Wallet-as-a-Service (WaaS) 2.0 API. By the end of this guide, you will be able to successfully call an API operation and receive a response.

## Before you begin

If you choose to use a WaaS SDK instead of manually writing the API requests, you need to first install the right version of the corresponding programming language. For example, if you want to use the [Python SDK](/developers/v2/developer-tools/quickstart-python), you need to have Python 3.7 or a newer version installed.

## Set up an account

Follow the instructions in [Set up your account and organization](https://manuals.cobo.com/en/portal/quick-start-guide) to set up your Cobo account and create your organization. If an organization has already been set up, ask your organization admin to invite you to join the organization.

<Note>This guide uses the development environment in all of its examples. Please create your organization in the development environment at [https://portal.dev.cobo.com/](https://portal.dev.cobo.com/).</Note>

## Generate an API key and an API secret

Generate an Ed25519 key pair as the API key and API secret. This guide uses OpenSSL as an example. To learn other methods for generating an API key and an API secret, see [Generate an API key and an API secret](/developers/v2/guides/overview/cobo-auth#generate-an-api-key-and-an-api-secret).

1. In a terminal window, run the following OpenSSL commands:

```shell theme={null}
# Generate a private key and save it in the `private.key.pem` file.
openssl genpkey -algorithm ed25519 -out private_key.pem

# Extract the public key from the private key and save it in the `public.key.pem` file.
openssl pkey -in private_key.pem -pubout -out public_key.pem
```

The private key is saved in the `private.key.pem` file, and the public key is saved in the `public.key.pem` file.

2. You can print the keys by running the following commands:

```
# Export the private key in hexadecimal format.
openssl pkey -in private_key.pem -text | grep 'priv:' -A 3 | tail -n +2 | tr -d ':\n '

# Export the public key in hexadecimal format.
openssl pkey -pubin -in public_key.pem -text | grep 'pub:' -A 3 | tail -n +2 | tr -d ':\n '
```

## Register the API key

Register your API key and configure related permissions on Cobo Portal. To learn more about registering an API key, see [Register an API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key).

1. Log in to [Cobo Portal](https://portal.dev.cobo.com/login) (development environment).
2. On the left navigation menu, click **Developer** > **API Keys**.
3. Click **Register API Key**.
4. Enter the API key name (maximum 30 characters).
5. Enter the public key you have generated in the previous step.
6. Under **Role & Wallet Scope**, set **Viewer** as the user role and **All Wallets** as the wallet scope. Each user role is permitted to call a specific set of operations, and the wallet scope determines the set of wallets this API key can access.
7. Click **Confirm** to save the changes.
8. Select **Temporary** as the key type. <Note>If you already have a static IP address, you can select **Permanent** as the key type instead and enter your IP address in **IP Whitelist**.</Note>
9. Click **Register**.
10. Notify your organization admins to approve the request on Cobo Guard.
    <Note>By default, it requires the approval of at least half of the admins to successfully register an API key. </Note>

You can only start using an API key after its status becomes **Active**.

## Authenticate your requests

<Note>You can skip this step if you choose to [use a WaaS SDK](/developers/v2/developer-tools/quickstart-python), which encapsulates the authentication mechanism.</Note>

To authenticate your API request, you need to provide your API key, a nonce, and the API signature as request headers. For more information, see [Cobo Auth](/developers/v2/guides/overview/cobo-auth).

```
headers = {
  "Biz-Api-Key": {YOUR_API_KEY}.hex(),
  "Biz-Api-Nonce": {Nonce},
  "Biz-Api-Signature": {YOUR_API_SIGNATURE}.hex(),
}
```

* Biz-Api-Key: The API key. To learn how to generate an API key, see [Generate an API key and an API secret](/developers/v2/guides/overview/cobo-auth#generate-an-api-key-and-an-api-secret).
* Biz-Api-Nonce: A random string used as the request nonce.
* Biz-Api-Signature: The API signature. To learn how to calculate an API signature, see [Calculate an API Signature](/developers/v2/guides/overview/cobo-auth#calculate-the-api-signature).

## Send a request

<Note>You can skip this step if you choose to [use a WaaS SDK](/developers/v2/developer-tools/quickstart-python), which offers ready-to-use functions that handle the API integration using the programming language of your project.</Note>

This guide uses the [List supported chains](/developers/v2/api-references/wallets/list-supported-chains) operation as an example to demonstrate how to send an API request. This operation retrieves all chains supported by a specific wallet type or subtype. In the following example, we retrieve all chains supported by [Custodial Wallets](https://manuals.cobo.com/en/portal/custodial-wallets/introduction).

```CURL theme={null}
curl --location --request GET 'https://api.dev.cobo.com/v2/wallets/chains?wallet_type=Custodial&wallet_subtype=&chain_ids=&limit=10&before=&after='
  
  # Replace the following with your own authentication information
  --header 'BIZ-API-KEY: {YOUR_API_KEY}' \
  --header 'Biz-Api-Nonce: {NONCE}' \
  --header 'Biz-Api-Signature: {YOUR_API_SIGNATURE}'
```

If the request is successful, you should receive the following response:

```JSON theme={null}
{
    "data": [
        {
            "chain_id": "ARBITRUM_ETH",
            "symbol": "Arbitrum",
            "icon_url": "https://d.cobo.com/public/logos/ARB.png",
            "explorer_tx_url": "https://arbiscan.io/tx/{txn_id}",
            "explorer_address_url": "https://arbiscan.io/address/{address}",
            "require_memo": false
        },
        {
            "chain_id": "AVAXC",
            "symbol": "Avalanche C-Chain",
            "icon_url": "https://d.cobo.com/public/logos/AVAXC-logo.png",
            "explorer_tx_url": "https://avascan.info/blockchain/c/tx/{txn_id}",
            "explorer_address_url": "https://avascan.info/blockchain/c/address/{address}",
            "require_memo": false
        },
        ...
    ],
    "pagination": {
        "before": "",
        "after": "41KxruMakf",
        "total_count": 19
    }
}
```

## Use a WaaS SDK

This section introduces how to use the Python SDK to call an API operation instead of manually writing the request.

To learn how to install the Python SDK and complete the initial setup, refer to [Get started with Python SDK](/developers/v2/developer-tools/quickstart-python).

The following is the sample code for calling the [List supported chains](/developers/v2/api-references/wallets/list-supported-chains) operation. When configuring the HTTP host, please use the URL of the development environment because you have registered the API key in the development environment in the previous step.

```python theme={null}
import cobo_waas2
from pprint import pprint

configuration = cobo_waas2.Configuration(
   # Replace `<YOUR_API_SECRET>` with your API secret.
   api_private_key="<YOUR_API_SECRET>",
   # Use the development environment 
   host="https://api.dev.cobo.com/v2"
)

# Enter a context with an instance of the API client
with cobo_waas2.ApiClient(configuration) as api_client:
   # Create an instance of the API class
   api_instance = cobo_waas2.WalletsApi(api_client)
   try:
       # List all supported chains
       api_response = api_instance.list_supported_chains()
       print("The response of WalletsApi->list_supported_chains:\n")
       pprint(api_response)
   except Exception as e:
       print("Exception when calling WalletsApi->list_supported_chains: %s\n" % e)
```

## What’s next

You have successfully sent an API request and received a response. However, there are still a few things to do before you can create a wallet, make a transaction, or implement other features.

* To start using a wallet, you must purchase a pricing plan or activate a trial plan if it is available. To learn about pricing plans and bills and payments, refer to [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction).
* To withdraw tokens from your wallet, you must first set up a callback endpoint to receive and approve withdrawal requests. It is highly recommended that you also set up a webhook endpoint to receive real-time notifications regarding transaction status updates and other events of your concern. To learn how to set up and register webhook and callback endpoints, refer to [Introduction to webhooks and callbacks](/developers/v2/guides/webhooks-callbacks/introduction).

## See also

* To learn what Cobo Portal has to offer, including how to choose from the four wallet technologies, refer to [Introduction](https://manuals.cobo.com/en/portal/introduction).

* To learn the specifics of the WaaS 2.0 API, see [API References](/developers/v2/api-references) or download the WaaS 2.0 API specification from [GitHub](https://github.com/CoboGlobal/developer-site/blob/master/v2/cobo_waas2_openapi_spec/dev_openapi.yaml).

* To learn the complete process of creating and interacting with Custodial Wallets (Asset Wallets), see [Get started with Custodial Wallets (Asset Wallets)](/developers/v2/guides/custodial-wallets/get-started-asset-wallets).

* To learn where to view API-related data and logs, see [Introduction to Developer Console](https://manuals.cobo.com/en/portal/developer-console/introduction).


# Balances and transaction amounts for MPC Wallets
Source: https://cobo.com/developers/v2/guides/mpc-wallets/balance-amounts

Understand balances and transaction amounts in MPC Wallets.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

The [List token balances by address](/developers/v2/api-references/wallets/list-token-balances-by-address) operation returns four types of balances and transaction amounts in the `data.balance` property. This article explains the definitions of these values and when they are updated during a transaction in MPC Wallets.

## Definitions

| Property                 | Type              | Definition                                                                                                                                                                         |
| ------------------------ | ----------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `data.balance.total`     | Current balance   | The current amount of tokens in an address, which is retrieved directly from the network.                                                                                          |
| `data.balance.pending`   | Pending amount    | The total amount being sent in a transaction, which is calculated as the withdrawal amount plus the transaction fee.                                                               |
| `data.balance.locked`    | Locked amount     | For UTXO chains, this is the combined value of the selected UTXOs for the transaction, which might exceed the pending amount. For other chains, it is equal to the pending amount. |
| `data.balance.available` | Available balance | The amount of tokens ready to be spent, which is calculated as the current balance minus the pending amount.                                                                       |

This diagram illustrates the relationship between these values:

<img alt="Definitions of several types of balances and amounts" />

## Update time

These values are updated at different times during a deposit and withdrawal transaction.

### Deposits

1. The current balance is updated when the transaction receives the first block confirmation.
2. If a reorganization occurs, the current balance will be updated to reflect the latest balance on the blockchain.

### Withdrawals

1. When a withdrawal request is submitted:
   * Current balance: Not updated
   * Pending amount: Equal to 0
   * Locked amount: Equal to 0
   * Available balance: Equal to the current balance
2. When the transaction is in the `PendingSignature` sub-status:
   * Current balance: Not updated.
   * Pending amount: The withdrawal amount plus the transaction fee.
   * Locked amount: For UTXO chains, this is the combined value of the selected UTXOs for the transaction. For other chains, it is equal to the Pending amount.
   * Available balance: The current balance minus the pending amount.
3. When the transaction receives the first block confirmation:
   * Current balance: Updated
   * Pending amount: Equal to 0
   * Locked amount: Equal to 0
   * Available balance: Equals to the current balance
4. When a reorganization occurs, all values are reverted back to the point when the transaction is in the `PendingSignature` sub-status:
   * Current balance: Reverted back to the original balance.
   * Pending amount: The withdrawal amount plus the transaction fee.
   * Locked amount: For UTXO chains, this is the combined value of the selected UTXOs for the transaction. For other chains, it is equal to the pending amount.
   * Available balance: The current balance minus the pending amount.
5. If the transaction fails:
   * Current balance: Reverted back to the original balance.
   * Pending amount: Equal to 0
   * Locked amount: Equal to 0
   * Available balance: Equal to the current balance

## Replace-By-Fee (RBF) transactions

If you speed up a transaction with an RBF transaction, the RBF transaction will be used in calculating the pending amount and locked amount.

If you cancel a transaction with an RBF transaction, the original transaction will be used in calculating the pending amount and locked amount.

## Maximum transferable amount

The maximum amount you can withdraw is affected by the transaction fee, available balance, and locked amount:

* (Withdrawal amount + transaction fee) > Available balance: The withdrawal request cannot be submitted.
* (Withdrawal amount + transaction fee) ≤ (Current balance - locked amount): Your withdrawal request will be handled immediately.
* (Current balance - locked amount) \< (Withdrawal amount + transaction fee) ≤ Available balance: You can successfully submit your withdrawal request, but your transaction will be queued.


# Integrate MPC Wallets (Organization-Controlled Wallets)
Source: https://cobo.com/developers/v2/guides/mpc-wallets/get-started-ocw



<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

After you have familiarized yourself with MPC Wallets through the [Cobo Portal quick start guide](https://manuals.cobo.com/en/portal/quick-start-guide-mpc), this guide will help you seamlessly integrate the MPC Wallet (Organization-Controlled Wallets) functionality into your application using the WaaS 2.0 API.

Following this guide, you'll learn how to:

1. Create a wallet
2. Deposit and withdraw tokens
3. Query wallet balances

<Note>This guide uses the [development environment](/developers/v2/guides/overview/environments) in all its code samples. It is recommended that you use the development environment to test your new features first before deploying them to the production environment. </Note>

## Technical architecture

Before you begin, it's helpful to understand the technical architecture of MPC Wallets, including the relationships between vaults, wallets, addresses, and key shares. The following diagram illustrates the components within a fully-functioning MPC vault:

<img alt="The components within a fully-functioning MPC vault" />

* An Organization-Controlled Wallet is always associated with a vault. A vault is a collection of Organization-Controlled Wallets that share the same root extended public/private key pairs.
* <a name="root-extended-public-keys" />Root extended public keys: A root extended public key is used in hierarchical deterministic (HD) wallets to derive multiple child public keys and addresses. Each vault has two root extended public keys, one derived from the Secp256k1 curve (used by chains such as Bitcoin and Ethereum) and the other derived from the EdDSA curve (used by chains such as Solona and TON). To learn more about root extended public keys, see [Key derivation](https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki#specification-key-derivation).
* Key share holders: Each vault can have multiple types of key share holders, including Main Key, Signing Key, and Recovery Key. Each key share holder has a set of TSS Nodes storing the private key shares that can collectively authorize a transaction or recover the root extended private key. For Main Key and Signing Key, one key share is generated within and stored encrypted in Cobo's multi-cloud infrastructure on your behalf. To learn more about key share holders, see [Key share holders overview](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/holder-group-overview).
* TSS key share groups: Each TSS key share group consists of two or three private key shares, depending on the number of holders. Each key share group can form a key pair with the root extended public key derived from the same curve. Each key share is unique.

## Prerequisites

* Before you call the WaaS API to create a wallet, you must first follow the instructions in the [Cobo Portal quick start guide](https://manuals.cobo.com/en/portal/quick-start-guide-mpc#set-up-an-mpc-vault) to set up a vault.
* Follow the instructions in [Send your first request](/developers/v2/guides/get-started/get-started-with-waas) to set up your account and send your first API request to the WaaS 2.0 service.
* If you choose to use a WaaS SDK instead of manually writing the API requests, refer to the SDK guide corresponding to the programming language of your choice ([Python](/developers/v2/developer-tools/quickstart-python), [Java](https://github.com/CoboGlobal/cobo-waas2-java-sdk), [Go](/developers/v2/developer-tools/quickstart-go), [JavaScript](https://github.com/CoboGlobal/cobo-waas2-js-sdk)) to integrate the SDK into your project.

## 1. Create a wallet

Once you have set up a vault, create a key share holder, and generate key shares, you can proceed to create a wallet. Call the [Create wallet](/developers/v2/api-references/wallets/create-wallet) operation and specify the properties in the request body as follows:

* `name`: Your wallet name.
* `wallet_type`: `MPC`.
* `wallet_subtype`:`Org-Controlled`.
* `vault_id`: The ID of the vault you have just created.

Upon successful completion of the request, the response will include the wallet ID, which is the unique identifier of the wallet you have just created. Store this wallet ID as you will need it for subsequent steps.

<Accordion title="Sample code in Python">
  ```py theme={null}
  import json
  import cobo_waas2
  from cobo_waas2.models.create_wallet_params import CreateWalletParams
  from cobo_waas2.models.created_wallet_info import CreatedWalletInfo
  from cobo_waas2.models.wallet_subtype import WalletSubtype
  from cobo_waas2.models.wallet_type import WalletType
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # Defining the host is optional and defaults to https://api.dev.cobo.com/v2
  # See configuration.py for a list of all supported configuration parameters.
  configuration = cobo_waas2.Configuration(
      api_private_key="<YOUR_API_SECRET>",
      host="https://api.dev.cobo.com/v2"
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsApi(api_client)
      create_wallet_params = cobo_waas2.CreateWalletParams(
          actual_instance=cobo_waas2.CreateMpcWalletParams(
              name="<YOUR_WALLET_NAME>",
              wallet_type=WalletType.MPC,
              wallet_subtype=WalletSubtype.ORG_CONTROLLED,
              vault_id="<YOUR_VAULT_ID>"
          )
      )

      try:
          # Create a wallet
          api_response = api_instance.create_wallet(create_wallet_params=create_wallet_params)
          print("The response of WalletsApi->create_wallet:\n")
          print(json.dumps(api_response.to_dict(), indent=2))
      except Exception as e:
          print("Exception when calling WalletsApi->create_wallet: %s\n" % e)
  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.*;

  public class CreateWalletExample {
      public static void main(String[] args) {
          ApiClient defaultClient = Configuration.getDefaultApiClient();
          // Use the development environment
          defaultClient.setEnv(Env.DEV);
          // Replace `<YOUR_API_SECRET>` with your API secret
          defaultClient.setPrivKey("<YOUR_API_SECRET>");
          WalletsApi apiInstance = new WalletsApi();
          try {
              CreateMpcWalletParams params = new CreateMpcWalletParams()
                      .name("OCW Example Wallet Demo(Java)")
                      .walletType(WalletType.MPC)
                      .walletSubtype(WalletSubtype.ORG_CONTROLLED)
                      .vaultId("<YOUR_VAULT_ID>");
              CreatedWalletInfo result = apiInstance.createWallet(new CreateWalletParams(params));
              System.out.println(result);
          } catch (ApiException e) {
              System.err.println("Exception when calling WalletsApi#createWallet");
              System.err.println("Status code: " + e.getCode());
              System.err.println("Reason: " + e.getResponseBody());
              System.err.println("Response headers: " + e.getResponseHeaders());
              e.printStackTrace();
          }
      }
  }

  ```
</Accordion>

## 2. Deposit and withdraw tokens

After setting up an Organization-Controlled Wallet, it is time to deposit some tokens into it and learn how to make withdrawals.

### Generate deposit addresses

To receive tokens, you need to generate deposit addresses within the wallet. To do so, call the [Create addresses in wallet](/developers/v2/api-references/wallets/create-addresses-in-wallet) operation and specify the parameters and properties as follows:

* Path:
  * `wallet_id`: The ID of the wallet you have just created.
* Request body:
  * `chain_id`: The ID of the blockchain.
  * `count`: Use this parameter to specify the number of addresses you want to create.

Upon successful completion of the request, the response will include the addresses you have just created. You can now proceed to deposit tokens into these addresses.

<Accordion title="Sample code in Python">
  ```py theme={null}
  import json

  import cobo_waas2
  from cobo_waas2 import (
     CreateAddressRequest,
     AddressEncoding,
  )

  configuration = cobo_waas2.Configuration(
     # Replace `<YOUR_API_SECRET>` with your API secret
     api_private_key="<YOUR_API_SECRET>",
     # Use the development environment
     host="https://api.dev.cobo.com/v2"
  )

  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
     # Create an instance of the API class
     wallet_api_instance = cobo_waas2.WalletsApi(api_client)
     try:
         # Generate two addresses on the Bitcoin testnet3 (XTN) chain using P2TR encoding
         api_response = wallet_api_instance.create_address(
             wallet_id="<Your Wallet ID>",
             create_address_request=CreateAddressRequest(
                 chain_id="XTN", count=2, encoding=AddressEncoding.ENCODING_P2_TR
             ),
         )
         print("The response of WalletsApi->create_address:")
         for address_info in api_response:
             print(json.dumps(address_info.to_dict(), indent=2))

     except Exception as e:
         print("Exception when calling WalletsApi->create_address, %s\n", e)
  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.AddressEncoding;
  import com.cobo.waas2.model.AddressInfo;
  import com.cobo.waas2.model.CreateAddressRequest;

  import java.util.List;
  import java.util.UUID;

  public class CreateAddressExample {
      public static void main(String[] args) {
          ApiClient defaultClient = Configuration.getDefaultApiClient();
          // Use the development environment
          defaultClient.setEnv(Env.DEV);
          // Replace `<YOUR_API_SECRET>` with your API secret
          defaultClient.setPrivKey("<YOUR_API_SECRET>");
          WalletsApi apiInstance = new WalletsApi();
          try {
              UUID wallet_id = UUID.fromString("<YOUR_WALLET_ID>");
              CreateAddressRequest params = new CreateAddressRequest()
                      .chainId("XTN")
                      .count(2)
                      .encoding(AddressEncoding.BECH32);
              List<AddressInfo> result = apiInstance.createAddress(wallet_id, params);
              for (AddressInfo addressInfo : result)
                  System.out.println(addressInfo);
          } catch (ApiException e) {
              System.err.println("Exception when calling WalletsApi#createAddress");
              System.err.println("Status code: " + e.getCode());
              System.err.println("Reason: " + e.getResponseBody());
              System.err.println("Response headers: " + e.getResponseHeaders());
              e.printStackTrace();
          }
      }
  }

  ```
</Accordion>

### Process deposit

After depositing tokens to the addresses you have generated, you can track the status of your deposit using one of the following two options. Compared with using API to query the transaction status, webhooks can give you real-time notifications and are thus the recommended option.

#### Option 1: Use webhooks for real-time notifications

Webhook is an essential mechanism for the WaaS service to communicate with your application. After you register a webhook endpoint on Cobo Portal, the WaaS service sends push messages to the designated URL when an event occurs.

To learn how to set up a webhook endpoint and register it on Cobo Portal, refer to [Introduction to webhooks and callbacks](/developers/v2/guides/webhooks-callbacks/introduction).

To track the status of your deposit, you can subscribe to the following webhook event types:

* wallets.transaction.created
* wallets.transaction.updated
* wallets.transaction.succeeded
* wallets.transaction.failed

To learn the trigger condition and data structure of each event type, refer to [Webhook event types and data types](/developers/v2/guides/webhooks-callbacks/webhook-event-type).

#### Option 2: Get transaction status by API call

To query the status of a deposit transaction, call the [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation and set the query parameters as follows:

* `types`: `Deposit`.
* `statuses`: `Confirming, Completed`. If you are depositing from an external address, you will be able to query the transaction details when the transaction is waiting for the required number of confirmations or when it is successfully executed.
* `wallet_ids`: The ID of the wallet you have created in the first step.

<Accordion title="Sample code in Python">
  ```python theme={null}
  import json
  import uuid


  import cobo_waas2
  from cobo_waas2 import (
     CreateAddressRequest,
     AddressEncoding,
     TransferParams,
     TransferSource,
     MpcTransferSource,
     WalletSubtype,
     TransferDestination, AddressTransferDestination, TransferDestinationType, AddressTransferDestinationAccountOutput,
  )


  configuration = cobo_waas2.Configuration(
     # Replace `<YOUR_API_SECRET>` with your API secret.
     api_private_key="<YOUR_API_SECRET>",
     # Use the development environment.
     host="https://api.dev.cobo.com/v2"
  )


  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
     # Create an instance of the API class
     transaction_api_instance = cobo_waas2.TransactionsApi(api_client)
     try:
         # List deposit transactions
         api_response = transaction_api_instance.list_transactions(
             types="Deposit",
             statuses="Confirming, Completed",
             wallet_ids="<YOUR_WALLET_ID>"
         )
         print("The response of TransactionsApi->list_transactions:")
         print(json.dumps(api_response.to_dict(), indent=2))


     except Exception as e:
         print("Exception when calling TransactionsApi->list_transactions, %s\n", e)
  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.ListTransactions200Response;


  import java.util.UUID;


  public class ListTransactionsExample {
     public static void main(String[] args) {
         ApiClient defaultClient = Configuration.getDefaultApiClient();
         // Use the development environment
         defaultClient.setEnv(Env.DEV);
         // Replace `<YOUR_API_SECRET>` with your API secret
         defaultClient.setPrivKey("<YOUR_API_SECRET>");
         TransactionsApi apiInstance = new TransactionsApi();
         try {
             String requestId = null;
             String coboIds = null;
             String transactionIds = null;
             String transactionHashes = "";
             String types = "Deposit";
             String statuses = "Confirming, Completed";
             String walletIds = "<YOUR_WALLET_ID>";
             String chainIds = null;
             String tokenIds = null;
             String assetIds = null;
             UUID vaultId = null;
             UUID projectId = null;
             Long minCreatedTimestamp = null;
             Long maxCreatedTimestamp = null;
             Integer limit = 50;
             String before = null;
             String after = null;


             ListTransactions200Response result = apiInstance.listTransactions(
                     requestId, coboIds, transactionIds, transactionHashes, types, statuses, walletIds, chainIds,
                     tokenIds, assetIds, vaultId, projectId, minCreatedTimestamp, maxCreatedTimestamp, limit, before, after);
             System.out.println(result);
         } catch (ApiException e) {
             System.err.println("Exception when calling WalletsApi#createAddress");
             System.err.println("Status code: " + e.getCode());
             System.err.println("Reason: " + e.getResponseBody());
             System.err.println("Response headers: " + e.getResponseHeaders());
             e.printStackTrace();
         }
     }
  }
  ```
</Accordion>

### Withdraw tokens

Now that you have tokens in your wallet, let's walk through the withdrawal process. Before making your first withdrawal, there are two important things to understand:

1. **The withdrawal process**: A withdrawal involves multiple steps including initiation, double confirmation, risk control checks, and transaction signing. For a detailed overview of each step, see [Transfer from MPC Wallets (Organization-Controlled Wallets)](https://manuals.cobo.com/en/portal/transfers/from-mpc-wallets#withdrawal-process).

2. **Callback endpoint setup**: For enhanced security, you should set up a callback endpoint to double confirm withdrawal requests. When you initiate a withdrawal via the WaaS 2.0 API, this endpoint will receive the transaction details and must confirm them before the transaction proceeds. To set this up, follow our guide on [webhooks and callbacks](/developers/v2/guides/webhooks-callbacks/introduction).

#### Initiate a withdrawal

Once you understand these concepts, you can initiate a withdrawal by calling the [Transfer token](/developers/v2/api-references/transactions/transfer-token) operation. Set the properties in the request body as follows:

* `request_id`: Your request ID.
* `source.source_type`: `Org-Controlled`.
* `source.wallet_id`: The ID of the wallet you have just created.
* `token_id`: The ID of the token you want to withdraw.
* `destination.destination_type`: `Address`.
* `destination.account_output`: The receiving address and memo (if applicable), and the amount you want to withdraw.
* `category_names`: The custom category for you to identify your transactions.
* `description`: The description of the transfer.

<Accordion title="Sample code in Python">
  ```py theme={null}
  import json
  import uuid

  import cobo_waas2
  from cobo_waas2 import (
     CreateAddressRequest,
     AddressEncoding,
     TransferParams,
     TransferSource,
     MpcTransferSource,
     WalletSubtype,
     TransferDestination, AddressTransferDestination, TransferDestinationType, AddressTransferDestinationAccountOutput,
  )

  configuration = cobo_waas2.Configuration(
     # Replace `<YOUR_API_SECRET>` with your API secret
     api_private_key="<YOUR_API_SECRET>",
     # Use the development environment
     host="https://api.dev.cobo.com/v2"
  )

  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
     # Create an instance of the API class
     transaction_api_instance = cobo_waas2.TransactionsApi(api_client)
     try:
         # Withdraw Bitcoin testnet3(XTN) tokens from the wallet
         api_response = transaction_api_instance.create_transfer_transaction(
             transfer_params=TransferParams(
                 request_id=str(uuid.uuid4()),
                 source=TransferSource(
                     actual_instance=MpcTransferSource
                     (
                         source_type=WalletSubtype.ORG_CONTROLLED,
                         wallet_id="<YOUR_WALLET ID>",
                     )
                 ),
                 token_id="XTN",
                 destination=TransferDestination(
                     actual_instance=AddressTransferDestination(
                         destination_type=TransferDestinationType.ADDRESS,
                         account_output=AddressTransferDestinationAccountOutput(
                             address="<TARGET_ADDRESS>",
                             amount="<TRANSFER_AMOUNT>"
                         )
                     )
                 ),
                 category_names=["<CATEGORY_NAME>"],
                 description="<DESCRIPTION>",
             )
         )
         print("The response of TransactionsApi->create_transfer_transaction:")
         print(json.dumps(api_response.to_dict(), indent=2))

     except Exception as e:
         print("Exception when calling TransactionsApi->create_transfer_transaction, %s\n", e)
  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  import java.util.ArrayList;
  import java.util.List;
  import java.util.UUID;

  public class TransferExample {
      public static void main(String[] args) {
          ApiClient defaultClient = Configuration.getDefaultApiClient();
          // Use the development environment
          defaultClient.setEnv(Env.DEV);
          // Replace `<YOUR_API_SECRET>` with your API secret
          defaultClient.setPrivKey("<YOUR_API_SECRET>");
          TransactionsApi apiInstance = new TransactionsApi();
          try {
              UUID walletId = UUID.fromString("<YOUR_WALLET_ID>");

              TransferParams params = new TransferParams();
              params.setRequestId("Demo" + UUID.randomUUID());

              MpcTransferSource transferSource = new MpcTransferSource().sourceType(WalletSubtype.ORG_CONTROLLED).walletId(walletId);
              params.setSource(new TransferSource(transferSource));

              params.setTokenId("XTN");
              AddressTransferDestination addressTransferDestination = new AddressTransferDestination()
                      .destinationType(TransferDestinationType.ADDRESS)
                      .accountOutput(new AddressTransferDestinationAccountOutput()
                              .address("<TARGET_ADDRESS>")
                              .amount("<TRANSFER_AMOUNT>"));
              params.setDestination(new TransferDestination(addressTransferDestination));

              List<String> categoryNames = new ArrayList<>();
              categoryNames.add("<Category Example>");
              params.categoryNames(categoryNames).description("<Description Example>");

              CreateTransferTransaction201Response result = apiInstance.createTransferTransaction(params);
              System.out.println(result);
          } catch (ApiException e) {
              System.err.println("Exception when calling TransactionsApi#createTransferTransaction");
              System.err.println("Status code: " + e.getCode());
              System.err.println("Reason: " + e.getResponseBody());
              System.err.println("Response headers: " + e.getResponseHeaders());
              e.printStackTrace();
          }
      }
  }
  ```
</Accordion>

The response of the withdrawal request is as follows. Record the transaction ID as you will use it in the following steps.

```json theme={null}
{
   "request_id": "<YOUR_REQUEST_ID>",
   "transaction_id": "<THE_GENERATED_TRANSACTION_ID>",
   "status": "Submitted"
}
```

#### Confirm withdrawal

After initiating a withdrawal, if you have configured a callback endpoint, the endpoint will receive a message containing the transaction details. Verify that the transaction matches your expectations, then approve it by responding with a success status code (200 or 201) and a response body containing 'ok'. For more information about handling callback messages, please refer to [
Implement handling logic](/developers/v2/guides/webhooks-callbacks/set-up-endpoint#implement-handling-logic).

#### Sign the transaction

After the withdrawal is confirmed, it will be sent to the corresponding signers based on your signing mode and signer types. The transaction will remain pending until it receives the necessary signature.

* For mobile signers, please notify them to open the Cobo Guard app and sign the transaction.
* For server signers, you can check if a signer is online through Cobo Portal:
  1. Log in to [Cobo Portal](https://portal.cobo.com/login).
  2. Click <img /> > **MPC Wallets**.
  3. Select your vault and then click the **Key Share Management** icon <img /> on the upper right hand corner.
  4. In the **Key Share Management** page, locate your server signer, and check the status indicator:

     * 🟢 Green dot: The signer is online and ready to sign transactions
     * No dot: The signer is offline and cannot sign transactions.

     <img alt="Key Share Management page showing signer status" />

#### Monitor the withdrawal status

In addition to webhook events, you can also call the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operation to query the status of the transaction. Set the path parameter `transaction_id` to the transaction ID returned in the response of the previous withdrawal request.

<Accordion title="Sample code in Python">
  ```py theme={null}
  import json
  import uuid


  import cobo_waas2
  from cobo_waas2 import (
     CreateAddressRequest,
     AddressEncoding,
     TransferParams,
     TransferSource,
     MpcTransferSource,
     WalletSubtype,
     TransferDestination, AddressTransferDestination, TransferDestinationType, AddressTransferDestinationAccountOutput,
  )


  configuration = cobo_waas2.Configuration(
     # Replace `<YOUR_API_SECRET>` with your API secret.
     api_private_key="<YOUR_API_SECRET>",
     # Use the development environment.
     host="https://api.dev.cobo.com/v2"
  )


  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
     # Create an instance of the API class
     transaction_api_instance = cobo_waas2.TransactionsApi(api_client)
     try:
         # Get transaction by ID
         api_response = transaction_api_instance.get_transaction_by_id(
             transaction_id="<YOUR_TRANSACTION_ID>"
         )
         print("The response of TransactionsApi->get_transaction_by_id:")
         print(json.dumps(api_response.to_dict(), indent=2))


     except Exception as e:
         print("Exception when calling TransactionsApi->get_transaction_by_id, %s\n", e)
  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.TransactionDetail;


  import java.util.UUID;


  public class GetTransactionExample {
     public static void main(String[] args) {
         ApiClient defaultClient = Configuration.getDefaultApiClient();
         // Use the development environment
         defaultClient.setEnv(Env.DEV);
         // Replace `<YOUR_API_SECRET>` with your API secret
         defaultClient.setPrivKey("<YOUR_API_SECRET>");
         TransactionsApi apiInstance = new TransactionsApi();
         try {
             UUID transactionId = UUID.fromString("<YOUR_TRANSACTION_ID>");


             TransactionDetail result = apiInstance.getTransactionById(transactionId);
             System.out.println(result);
         } catch (ApiException e) {
             System.err.println("Exception when calling TransactionsApi#getTransactionById");
             System.err.println("Status code: " + e.getCode());
             System.err.println("Reason: " + e.getResponseBody());
             System.err.println("Response headers: " + e.getResponseHeaders());
             e.printStackTrace();
         }
     }
  }
  ```
</Accordion>

## 3. Query wallet balances

After successfully withdrawing tokens from your wallet, you can call [List token balances by wallet](/developers/v2/api-references/wallets/list-token-balances-by-wallet) to query the wallet balances. Specify the path and query parameters as follows:

* `wallet_id`: The ID of the wallet you have just created.
* `token_ids`: You can leave it empty to query the balances of all tokens, or set it to the specific token you want to query.

<Accordion title="Sample code in Python">
  ```py theme={null}
  import json


  import cobo_waas2
  from cobo_waas2 import (
     WalletType,
     WalletSubtype,
  )


  configuration = cobo_waas2.Configuration(
     # Replace `<YOUR_API_SECRET>` with your API secret.
     api_private_key="<YOUR_API_SECRET>",
     # Use the development environment.
     host="https://api.dev.cobo.com/v2"
  )


  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
     # Create an instance of the API class
     wallet_api_instance = cobo_waas2.WalletsApi(api_client)
     try:
         # List token balances
         api_response = wallet_api_instance.list_token_balances_for_wallet(
             wallet_id="<YOUR_WALLET_ID>",
         )
         print(f"The response of WalletsApi->list_token_balances_for_wallet:")
         print(json.dumps(api_response.to_dict(), indent=2))


     except Exception as e:
         print("Exception when calling WalletsApi->list_token_balances_for_wallet, %s\n", e)
  ```
</Accordion>

<Accordion title="Sample code in Java">
  ```java theme={null}
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsApi;
  import com.cobo.waas2.model.ListTokenBalancesForAddress200Response;

  import java.util.UUID;

  public class ListTokenBalancesExample {
      public static void main(String[] args) {
          ApiClient defaultClient = Configuration.getDefaultApiClient();
          // Use the development environment
          defaultClient.setEnv(Env.DEV);
          // Replace `<YOUR_API_SECRET>` with your API secret
          defaultClient.setPrivKey("<YOUR_API_SECRET>");
          WalletsApi apiInstance = new WalletsApi();
          try {
              UUID wallet_id = UUID.fromString("<YOUR_WALLET_ID>");
              String tokenIds = null;
              Integer limit = 50;
              String before = null;
              String after = null;
              ListTokenBalancesForAddress200Response result = apiInstance.listTokenBalancesForWallet(wallet_id, tokenIds, limit, before, after);
              System.out.println(result);
          } catch (ApiException e) {
              System.err.println("Exception when calling WalletsApi#listTokenBalancesForWallet");
              System.err.println("Status code: " + e.getCode());
              System.err.println("Reason: " + e.getResponseBody());
              System.err.println("Response headers: " + e.getResponseHeaders());
              e.printStackTrace();
          }
      }
  }
  ```
</Accordion>


# Integrate MPC Wallets (User-Controlled Wallets)
Source: https://cobo.com/developers/v2/guides/mpc-wallets/get-started-ucw

Guide to building User-Controlled Wallets using the WaaS 2.0 API and the UCW SDK, covering setup, wallet creation, and transaction management.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This guide gets you started with using MPC Wallets (User-Controlled Wallets). For a high-level overview of what User-Controlled Wallets are, see [Introduction to User-Controlled Wallets](https://manuals.cobo.com/en/portal/mpc-wallets/introduction#user-controlled-wallets). By following this guide, you will be able to build a User-Controlled Wallet by using the [Cobo Wallet-as-a-Service (WaaS) 2.0 API](/developers/v2/guides/overview/introduction) and UCW SDK to:

<Steps>
  <Step title="Complete the initial setup">
    1. Create projects with the Client Backend or Cobo Portal
    2. Install the UCW SDK
    3. Initialize the UCW SDK
    4. Create a vault
    5. Create a Main Group

    <Steps />
  </Step>

  <Step title="Create a wallet and an address" />

  <Step title="Create a transaction" />

  <Step title="Back up and restore">
    1. Back up and restore your key shares with iCloud
    2. Create a Recovery Group
    3. Perform recovery from Recovery Group
    4. Perform disaster recovery
  </Step>
</Steps>

<Note>You can choose between the 2-2, 2-3, or 3-3 [signature scheme](https://manuals.cobo.com/en/portal/mpc-wallets/introduction#threshold-signature-scheme-tss) for your User-Controlled Wallets. For the purposes of this documentation, we will use the 2-2 signature scheme.</Note>

<Note>This guide uses the [development environment](/developers/v2/guides/overview/environments) in all its code samples. It is recommended that you use the development environment to test your new features first before deploying them to the production environment.</Note>

## Technical architecture

The following diagram illustrates the components within a fully-functioning User-Controlled Wallet:

<img alt="UCW's technical architecture" />

<Note>You only need to focus on implementing the Client Backend and Client App. The Cobo Backend, Cobo TSS Relay, and UCW SDK are managed and provided by Cobo.</Note>

Use the following tabs to learn more about each component in the technical architecture:

<Tabs>
  <Tab title="Client Backend">
    Your server responsible for interacting with the Cobo Backend using the WaaS 2.0 API. Client Backend is also used to communicate with your Client Apps. To get started, you can download our Client Backend Demo [here](https://github.com/CoboGlobal/cobo-ucw-demo-backend) to set up a working example of a User-Controlled Wallet before developing your own implementation.
  </Tab>

  <Tab title="Client App">
    A user-facing application you build that utilizes the UCW SDK to communicate with the Cobo TSS Relay. Client App is also used to communicate with your Client Backend. To get started, you can download our Client App Demo [here](https://github.com/CoboGlobal/cobo-ucw-demo-app-ios) to set up a working example of a User-Controlled Wallet before developing your own implementation.
  </Tab>

  <Tab title="Cobo Backend">
    The Cobo server that handles the WaaS 2.0 API calls from the Client Backend.
  </Tab>

  <Tab title="Cobo TSS Relay">
    A part of the Cobo Backend.
  </Tab>

  <Tab title="UCW SDK">
    The SDK provided by Cobo that allows your Client App to interact with the Cobo TSS Relay. To get started, you can download our UCW SDK Demo [here](https://github.com/CoboGlobal/cobo-ucw-sdk-ios.git) to set up a working example of a User-Controlled Wallet before developing your own implementation.
  </Tab>

  <Tab title="Server Co-Signer">
    This applies only if you're building a User-Controlled Wallet with a 2-3 or 3-3 [signature scheme](https://manuals.cobo.com/en/portal/mpc-wallets/introduction#threshold-signature-scheme-tss), where you will need to build a [server co-signer](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/holder-group-main-group#create-a-main-group) to sign transactions. Please note that for the 2-3 signature scheme, Cobo must be one of the signers, while the second signer can either be the UCW SDK in a Client App or the server co-signer.
  </Tab>
</Tabs>

<Info>To learn about the general architecture of an MPC Wallet, see Organization-Controlled Wallet's [Technical architecture](/developers/v2/guides/mpc-wallets/get-started-ocw#technical-architecture).</Info>

## Data model

The following diagram presents an example of a User-Controlled Wallet data model that you can reference when developing your own implementation. It provides a clear representation of how users, vaults, wallets, transactions, addresses, TSS requests, groups, and TSS Nodes interact in a working User-Controlled Wallet.

```mermaid theme={null}
erDiagram
    user[User] {
        string user_id
        string email
    }
    vault[Vault] {
        string cobo_vault_id
        string name
        string cobo_main_group_id
        string cobo_project_id
        int status
    }
    group["Group"] {
        string cobo_key_share_holder_group_id
        string cobo_vault_id
        int group_type
    }
    node["User TSS Node"] {
        string user_id
        string tss_node_id
        string holder_name
        int status
    }
    wallet[Wallet] {
        string cobo_vault_id
        string cobo_wallet_id
        string name
    }
    addr[Address] {
        string address
        string path
        string chain_id
        string cobo_wallet_id
    }
    request["TSS Request"] {
        string cobo_tss_request_id
        string cobo_target_key_holder_group_id
    }
    tx[Transaction] {
        string cobo_transaction_id
        string request_id
        string cobo_wallet_id
        string address
        string amount
        int type
    }

    user ||--|| vault: has
    user||--o{ node : "owns"
    vault ||--|{ wallet : contains
    vault ||--o{ request : "contains"
    vault ||--o{ group : "owns"
    wallet||--o{ tx : contains
    wallet ||--o{ addr : contains
    group ||--o{ node : contains
```

Use the tabs below to learn more about each entity and attribute in the data model.

<AccordionGroup>
  <Accordion title="User">
    #### Attributes:

    * `user_id`: Unique identifier for the user.
    * `email`: User's email address.

    #### Relationships:

    * **Has** a direct relationship with Vault, indicating that a user has exactly one vault and each vault corresponds to exactly one user.
    * **Owns** User TSS Node, where a user has zero or more TSS Nodes and each TSS Node is owned by exactly one user.
  </Accordion>

  <Accordion title="Vault">
    #### Attributes:

    * `cobo_vault_id`: Unique identifier for the vault in the Cobo system.
    * `name`: The name of the vault.
    * `cobo_main_group_id`: The currently active Main Group this vault owns that holds the authority to sign transactions.
      * <Info>Even though a vault can own multiple Main Groups and Recovery Groups, only one Main Group can be active at any given time.</Info>
    * `cobo_project_id`: The project to which the vault belongs.
    * `status`: The vault's current status.

    #### Relationships:

    * **Contains** Wallet, meaning that a vault can hold one or more wallets, and a wallet belongs to exactly one vault.
    * **Contains** TSS Request, showing that a vault may have zero or more pending or processed TSS requests, and each TSS request corresponds to exactly one vault.
    * **Owns** Group, indicating that a vault owns multiple Main Groups and Recovery Groups.
  </Accordion>

  <Accordion title="Wallet">
    #### Attributes:

    * `cobo_vault_id`: Identifier linking the wallet to the vault that contains this wallet.
    * `cobo_wallet_id`: Unique identifier for the wallet.
    * `name`: The name of the wallet.

    #### Relationships:

    * **Contains** Transaction, showing that a wallet can include zero or more transactions, and each transaction corresponds to exactly one wallet.
    * **Contains** Address, meaning a wallet can have zero or more blockchain addresses associated with it, and each address corresponds to exactly one wallet.
  </Accordion>

  <Accordion title="Transaction">
    #### Attributes:

    * `cobo_transaction_id`: Unique identifier for the transaction in the Cobo system.
    * `request_id`: The request ID associated with the transaction.
    * `cobo_wallet_id`: The wallet associated with the transaction.
    * `address`: The blockchain address involved in the transaction.
    * `amount`: The amount involved in the transaction.
    * `type`: Type of transaction (e.g., deposit, withdrawal).

    #### Relationships:

    * **Belongs to** Wallet, indicating that each transaction is linked to exactly one wallet.
  </Accordion>

  <Accordion title="Address">
    #### Attributes:

    * `address`: The blockchain address associated with the wallet.
    * `path`: The derivation path of the address.
    * `chain_id`: The ID of the blockchain network associated with the address.
    * `cobo_wallet_id`: Identifier linking the address to its wallet.

    #### Relationships:

    * **Belongs to** Wallet, indicating that each address is part of exactly one wallet.
  </Accordion>

  <Accordion title="TSS Request">
    #### Attributes:

    * `cobo_tss_request_id`: Unique identifier for the [TSS request](/developers/v2/api-references/wallets--mpc-wallets/create-tss-request).
    * `cobo_target_key_holder_group_id`: The target key share holder group involved in the TSS request.

    #### Relationships:

    * **Belongs to** Vault, showing that TSS requests are linked to exactly one vault, and each vault contains zero or more TSS requests.
  </Accordion>

  <Accordion title="Group">
    #### Attributes:

    * `cobo_key_share_holder_group_id`: Unique identifier for the [key share holder group](/developers/v2/guides/mpc-wallets/get-started-ocw#create-a-key-share-holder-group).
    * `cobo_vault_id`: Unique identifier for the vault that owns this key share holder group.
    * `group_type`: Type of key share holder group (i.e. Main Group or Recovery Group).

    #### Relationships:

    * **Contains** User TSS Node, meaning that a group can hold multiple TSS Nodes, and each TSS Node corresponds to exactly one group.
  </Accordion>

  <Accordion title="User TSS Node">
    #### Attributes:

    * `user_id`: Unique identifier for the user of the TSS Node.
    * `tss_node_id`: Unique identifier for the TSS Node.
    * `holder_name`: The name of the holder.
    * `status`: The status of the TSS Node.

    #### Relationships:

    * **Belongs to** Group, meaning that a key share holder group contains zero or more TSS Nodes, and each TSS Node belongs to exactly one key share holder group.
    * **Owned by** User. Each user owns to zero or more TSS Nodes, and each TSS Node is owned by exactly one user.
  </Accordion>
</AccordionGroup>

## Prerequisites

* Follow the instructions in [Send your first request](/developers/v2/guides/get-started/get-started-with-waas) to set up your account and send your first API request to the WaaS 2.0 service.
* If you choose to use a WaaS SDK instead of manually writing the API requests, refer to the SDK guide corresponding to the programming language of your choice ([Python](/developers/v2/developer-tools/quickstart-python), [Java](https://github.com/CoboGlobal/cobo-waas2-java-sdk), [Go](/developers/v2/developer-tools/quickstart-go), [JavaScript](https://github.com/CoboGlobal/cobo-waas2-js-sdk)) to integrate the SDK into your Client Backend.
* Prepare some test tokens as you will need them when testing the deposit feature. To know which test tokens you can use, refer to [Query chain and token information](https://www.cobo.com/developers/v2/guides/mpc-wallets/get-started-ocw#1-query-chain-and-token-information). In most cases, you can use XTN as the test token.
* It is highly recommended that you set up a callback endpoint to receive and approve withdrawal requests and a webhook endpoint to receive real-time notifications regarding transaction status updates and other events of your concern. To learn how to set up and register webhook and callback endpoints, refer to [Introduction to webhooks and callbacks](/developers/v2/guides/webhooks-callbacks/introduction).

## 1. Complete the initial setup

<Steps>
  <Step title="Create projects with the Client Backend or Cobo Portal.">
    You can create projects with either the Client Backend or directly on Cobo Portal.

    * To create projects with the Client Backend, call the [Create project](/developers/v2/api-references/wallets--mpc-wallets/create-project) operation.
    * To create projects with Cobo Portal, see our [upcoming Product Manuals for User-Controlled Wallets](https://manuals.cobo.com/en/portal/mpc-wallets/ucw/introduction).
  </Step>

  <Step title="Install UCW SDK">
    To install the UCW SDK, see our upcoming article on "Get started with UCW SDK", which shows how you can download the UCW SDK, add it to your iOS app development environment, initialize the UCW SDK in your Client App, and invoke a UCW SDK operation.
  </Step>

  <Step title="Initialize UCW SDK">
    This section outlines the sequence of operations for initializing the UCW SDK from a Client App. The initialization process is straightforward, with a single interaction between the Client App and the UCW SDK to ensure that the UCW SDK is set up and ready for further operations.

    The UCW SDK needs to be initialized in the Client App to facilitate communication with the Cobo TSS Relay. This initialization also sets up the TSS Node ID, a unique identifier for the node participating in key generation.

    ```mermaid theme={null}
    sequenceDiagram
        autonumber
        participant App as Client App
        participant SDK as UCW SDK

        App ->> SDK: Init
        activate App
        SDK ->> App: return success
        deactivate App
    ```

    #### Sequence of operations

    * **Initialize UCW SDK**

      * Client App → UCW SDK

        1. Client App sends a request to initialize the UCW SDK by calling the [Initialize Secrets](/developers/v2/developer-tools/ucw-sdk/initialize-secrets/initialize-secrets) operation.

      * UCW SDK → Client App

        2. UCW SDK returns a success message indicating that the initialization has been completed successfully.
  </Step>

  <Step title="Create a vault">
    This section explains the sequence of operations involved in creating a [vault](/developers/v2/guides/mpc-wallets/get-started-ocw#technical-architecture). The process involves interactions between the Client App, Client Backend, and the Cobo Backend.

    ```mermaid theme={null}
    sequenceDiagram
        autonumber
        participant App as Client App
        participant C as Client Backend
        participant P as Cobo Backend

        App ->> +C: POST /v1/vaults/initialize
        activate App
        C ->> +P: POST /v2/wallets/mpc/vaults , {project_id}
        P ->> -C: return {vault_id}
        C ->> C: bind {vault_id} to {user_id}
        C ->> -App: return {vault_info}
        deactivate App
    ```

    #### Sequence of operations

    * **Send vault creation request to Client Backend**

      * Client App → Client Backend

        1. Client App sends a request to the Client Backend to create a vault.

    * **Create the vault in Cobo Backend**

      * Client Backend → Cobo Backend

        2. Client Backend forwards the request to the Cobo Backend to create a new vault for the specified project by calling the [Create vault](/developers/v2/api-references/wallets--mpc-wallets/create-vault) operation.

      * Cobo Backend → Client Backend

        3. Cobo Backend responds with the newly created vault ID.

    * **Binding the vault to the user**

      * Client Backend

        4. Client Backend binds the newly created vault ID to an associated User ID.

    * **Return vault information to Client App**

      * Client Backend → Client App

        5. Client Backend returns the vault information, including the vault ID and other metadata, to the Client App.
  </Step>

  <Step title="Create a Main Group">
    This section details the sequence of operations involved in creating a Main Group and performing a key generation process using the Client App, UCW SDK, Client Backend, Cobo Backend, and Cobo TSS Relay.

    ```mermaid theme={null}
    sequenceDiagram
        autonumber
        participant App as Client App
        participant SDK as UCW SDK
        participant C as Client Backend
        participant P as Cobo Backend
        participant R as Cobo TSS Relay

        App ->> SDK: Open
        activate App
        SDK ->> App: SDKInstance
        App ->> SDK: SDKInstance.GetTSSNodeID
        SDK ->> App: return {tss_node_id}
        deactivate App

        App ->> +C: POST /v1/vaults/{vault_id}/tss/generate_main_group , {tss_node_id}
        C ->> P: POST /v2/wallets/mpc/vaults/{vault_id}/key_share_holder_groups , {type: main_group, key_share_holders}
        P ->> C: return {key_share_holder_group_id}
        C ->> C: bind {key_share_holder_group_id} to {vault_id}
        C ->> C: bind {tss_node_id} to {key_share_holder_group_id}
        C ->> +P: POST /v2/wallets/mpc/vaults/{vault_id}/tss_requests , {KeyGen}
        P ->> C: return {tss_request_id}
        C ->> -App: return {tss_request_id, status: PendingKeyHolderConfirmation}
        P ->> P: cobo risk control
        P ->> R: POST create_tss_request
        R ->> P: return 200 OK

        alt use webhook
            P ->> C: POST /v1/webhook , {tss_request_event_type, tss_request_info}
        else use polling
            C ->> P: GET /v2/wallets/mpc/vaults/{vault_id}/tss_requests/{tss_request_id}
            P ->> -C: return {tss_request_id, status: KeyGenerating}
        end

        activate App
        alt use push
            C ->> +App: push notification
        else use polling
            App ->> C: GET /v1/vaults/{vault_id}/tss/requests
            C ->> App: return {tss_request_id, status: KeyGenerating}
        end


        App ->> +SDK: SDKInstance.GetTSSRequests
        SDK ->> R: GetTSSRequests
        R ->> SDK: {tss_request_info}
        SDK ->> -App: {tss_request_info}
        App ->> App: review pending TSSRequest
        App ->> +SDK: SDKInstance.ApproveTSSRequest {tss_request_id}
        SDK ->> R: participate in keygen
        R ->> SDK: {keygen result}
        App ->> SDK: SDKInstance.GetTSSRequests
        SDK ->> -App: {tss_request_info}
        App ->> C: /v1/tss_requests/{tss_request_id}/report
        deactivate App

        R ->> P: {keygen result}

        alt use webhook
            P ->> C: POST /v1/webhook , {keygen result}
        else use polling
            C ->> P: GET /v2/wallets/mpc/vaults/{vault_id}/tss_requests/
            P ->> C: request_status: {keygen result}
        end

    ```

    #### Sequence of operations

    * **Open UCW SDK in the Client App**

      * Client App → UCW SDK

        1. Client App opens a UCW SDK instance by calling the [Create UCW class](/developers/v2/developer-tools/ucw-sdk/ucw-class/create-ucw) and [Create UCWPublic class](/developers/v2/developer-tools/ucw-sdk/ucwpublic-class/create-ucw-public) operations.

      * UCW SDK → Client App

        2. UCW SDK returns an instance of the UCWSDK and UCWSDKPublic class that is used for further interactions.

    * **Retrieve TSS Node ID**

      * Client App → UCW SDK

        3. Client App calls the [Get TSS Node ID](/developers/v2/developer-tools/ucw-sdk/ucwpublic-class/get-tss-node-id) operation on the UCWSDKPublic to retrieve the TSS Node ID.

      * UCW SDK → Client App

        4. UCW SDK responds with the TSS Node ID.

    * **Initialize Main Group creation**

      * Client App → Client Backend

        5. Client App sends a request to the Client Backend to generate the Main Group for the vault specified by vault ID, also passing the TSS Node ID.

      * Client Backend → Cobo Backend

        6. Client Backend calls the [Create key share holder group](/developers/v2/api-references/wallets--mpc-wallets/create-key-share-holder-group) operation, instructing the Cobo Backend to create a Main Group.

      * Cobo Backend → Client Backend

        7. Cobo Backend responds with a key share holder group ID, indicating that the Main Group has been successfully created.

      * Client Backend

        8. Client Backend binds the key share holder group ID to the vault ID.

        9. Client Backend binds the TSS Node ID with the key share holder group ID.

    * **Initialize key generation request**

      * Client Backend → Cobo Backend

        10. Client Backend calls the [Create TSS request](/developers/v2/api-references/wallets--mpc-wallets/create-tss-request) operation, instructing the Cobo Backend to initiate the key generation process.

      * Cobo Backend → Client Backend

        11. Cobo Backend responds with a TSS request ID and a status of the TSS request.

      * Client Backend → Client App

        12. Client Backend sends the TSS request ID and the TSS request status to the Client App, notifying the Client App that the TSS request is pending key share holder confirmations.

    * **Cobo Backend risk controls and TSS request creation**

      * Cobo Backend

        13. Cobo Backend performs risk control checks before forwarding the request to the Cobo TSS Relay.

      * Cobo Backend → Cobo TSS Relay

        14. Cobo Backend sends the request to the Cobo TSS Relay to create a TSS request.

      * Cobo TSS Relay → Cobo Backend

        15. Cobo TSS Relay confirms the request creation with a 200 OK response.

    * **Monitor the TSS request status on Client Backend**

      * Cobo Backend → Client Backend

        You can optionally monitor the status of the TSS request on the Client Backend through either webhook or polling.

        * **Webhook option**

          16. Cobo Backend sends a webhook to the Client Backend with the current status of the TSS request.

              <Info>To see the available webhook event types, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types).</Info>

              <Info>To see how to set up your Client Backend to receive webhook events, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).</Info>

        * **Polling option**

          17. Client Backend polls the Cobo Backend to retrieve the status of the TSS request by calling the [Get TSS request](/developers/v2/api-references/wallets--mpc-wallets/get-tss-request) operation.

          18. Cobo Backend returns the status of the TSS request.

      * **(Optional) Monitor TSS request status on Client App**

        * Client Backend → Client App

          You can optionally monitor the status of the TSS request on the Client App through either app notification or polling.

          * **App notification option**

            19. Client Backend pushes a notification to the Client App with the TSS request status.

          * **Polling option**

            20. Client App polls the Client Backend for the TSS request status.

            21. Client Backend returns the TSS request status.

    * **Review and approval of TSS request in Client App**

      * Client App → UCW SDK

        22. Client App calls the UCW SDK to get the pending TSS requests by calling the [Get TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests) operation.

      * UCW SDK → Cobo TSS Relay

        23. UCW SDK forwards the request to the Cobo TSS Relay.

        24. Cobo TSS Relay returns the TSS request information to UCW SDK.

      * UCW SDK → Client App

        25. The UCW SDK returns the TSS request information to the Client App.

      * Client App

        26. User reviews the TSS request on the Client App.

      * Client App → UCW SDK

        27. User uses the Client App to approve the TSS request. The Client App calls the [Approve TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/approve-tss-requests) operation and passes in the TSS request ID.

      * UCW SDK → Cobo TSS Relay

        28. UCW SDK participates in the key generation process by forwarding user's approval to the Cobo TSS Relay.

        29. Cobo TSS Relay returns the key generation result to the UCW SDK.

      * Client App → UCW SDK

        30. Client App checks the status of the TSS request with the UCW SDK by calling the [Get TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests) operation.

      * UCW SDK → Client App

        31. UCW SDK returns the updated status of the TSS request.

    * **Key generation result transmission**

      * Client App → Client Backend

        32. Client App sends the key generation result to the Client Backend.

      * Cobo TSS Relay → Cobo Backend

        33. Cobo TSS Relay sends the key generation result to the Cobo Backend.

    * **(Optional) Monitor key generation result on Client Backend**

      * Cobo Backend → Client Backend

        You can optionally monitor the key generation result on Client Backend through either webhook or polling.

        * **Webhook option**

          34. Cobo Backend sends the key generation result via a webhook event to the Client Backend.

              <Info>To see the available webhook event types, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types).</Info>

              <Info>To see how to set up your Client Backend to receive webhook events, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).</Info>

        * **Polling Option**

          35. Client Backend polls the Cobo Backend for the key generation result by calling the [Get TSS request](/developers/v2/api-references/wallets--mpc-wallets/get-tss-request) operation.

          36. Cobo Backend returns the key generation result.
  </Step>
</Steps>

## 2. Create a wallet and an address

<Steps>
  <Step title="">
    This section details the sequence of operations involved in creating a wallet and generating an address within your User-Controlled Wallets. The process involves interactions between the Client App, Client Backend, and Cobo Backend.

    ```mermaid theme={null}
    sequenceDiagram
        autonumber
        participant App as Client App
        participant C as Client Backend
        participant P as Cobo Backend

        App ->> +C: POST /v1/wallets/{wallet_id}/transactions/estimate_fee , {tx_data}
        C ->> +P: POST /v2/transactions/estimate_fee , {wallet_id, tx_data}
        P ->> -C: return {estimate_fee_info}
        C ->> -App: return {estimate_fee_info}

        App ->> App: select fee

        App ->> +C: POST /v1/wallets/{wallet_id}/transactions , {tx_data}
        C ->> +P: POST /v2/transactions/transfer , {tx_request_id, wallet_id, tx_data}
        P ->> C: return {transaction_id, transaction_info}
        C ->> -App: return {tx_request_id, transaction_id}
        P ->> P: cobo risk control
        P ->> +R: POST create_tss_request
        R ->> -P: return 200 OK
        P ->> -C: use [webhook] or [polling] , {transaction_event_type, transaction_info}

        activate App
        alt use push
            C ->> +App: push notification
        else use polling
            App ->> +C: GET /v1/wallets/{wallet_id}/transactions , {status: unfinished, transaction_info}
            C ->> -App: return {transaction_info}
        end

        App ->> +SDK: SDKInstance.GetTransactions, {transaction_id}
        SDK ->> +R: GetTransactions, {transaction_id}
        R ->> -SDK: {transaction_task_info}
        SDK ->> -App: {transaction_info}

        App ->> App: review transaction info
        App ->> +SDK: SDKInstance.ApproveTransactions {transaction_id}
        SDK ->> +R: participate in signing
        R ->> -SDK: {signature}
        App ->> SDK: SDKInstance.GetTransactions, {transaction_id}
        SDK ->> -App: {transaction_info}
        App ->> C: POST /v1/transactions/{transaction_id}/report
        deactivate App

        R ->> +P: {signature}
        P ->> -C: use [webhook] or [polling] , {transaction_event_type, transaction_info}


    ```

    #### Sequence of operations

    * **Estimate transaction fee**

      * Client App → Client Backend

        1. Client App initiates a fee estimation request by sending transaction data to the Client Backend.

      * Client Backend → Cobo Backend

        2. Client Backend forwards the request to the Cobo Backend to estimate the fee for the transaction by calling the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) operation.

      * Cobo Backend → Client Backend

        3. Cobo Backend processes the request and returns the estimated fee information.

      * Client Backend → Client App

        4. Client Backend returns the estimated fee information to the Client App.

      * Client App

        5. User reviews and selects the appropriate fee using the Client App.

    * **Submit transaction**

      * Client App → Client Backend

        6. After selecting the fee, the Client App submits the transaction data to the Client Backend for processing.

      * Client Backend → Cobo Backend

        7. Client Backend forwards the transaction data to the Cobo Backend to initiate the transaction by calling the [Transfer token](/developers/v2/api-references/transactions/transfer-token) operation.

      * Cobo Backend → Client Backend

        8. Cobo Backend processes the request and returns the transaction ID and other transaction information.

      * Client Backend → Client App

        9. Client Backend returns the transaction information to the Client App.

    * **Perform risk controls and TSS request processing**

      * Cobo Backend

        10. Cobo Backend performs internal risk control checks before proceeding with the transaction.

      * Cobo Backend → Cobo TSS Relay

        11. Cobo Backend sends a request to the Cobo TSS Relay to create a TSS request for the transaction.

      * Cobo TSS Relay → Cobo Backend

        12. Cobo TSS Relay confirms the creation of the TSS request with a 200 OK response.

    * **Monitor transaction status on Client Backend**

      * Cobo Backend → Client Backend

        (13) You can monitor the status of the transaction on the Client Backend through either webhook or polling.

        * **Webhook option**

          Cobo Backend sends transaction updates to the Client Backend using webhooks.

          <Info>To see the available webhook event types, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types).</Info>

          <Info>To see how to set up your Client Backend to receive webhook events, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).</Info>

        * **Polling option**

          Client Backend polls the Cobo Backend to get updates on the transaction status by calling the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operation.

          Cobo Backend returns the transaction status to the Client Backend.

    * **(Optional) Monitor transaction status on Client App**

      * Client Backend → Client App

        You can optionally send the transaction status to the Client App through push notifications or polling.

        * **Push notification option**

          14. Client Backend sends a push notification to the Client App with the transaction status.

        * **Polling option**

          15. Client App polls the Client Backend for the transaction status.

          16. Client Backend returns the transaction status to the Client App.

    * **Review and approve the transaction**

      * Client App → UCW SDK

        17. Client App calls the UCW SDK to retrieve detailed transaction information by calling the [Get transactions](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-transactions) operation.

      * UCW SDK → Cobo TSS Relay

        18. UCW SDK forwards the request to the Cobo TSS Relay to retrieve the transaction information.

        19. Cobo TSS Relay returns the transaction information to the UCW SDK.

      * UCW SDK → Client App

        20. UCW SDK returns the transaction information to the Client App.

      * Client App

        21. User reviews the transaction information on the Client App.

      * Client App → UCW SDK

        22. Client App approves the transaction using the UCW SDK by calling the [Approve transactions](/developers/v2/developer-tools/ucw-sdk/ucw-class/approve-transactions) operation, initiating the signing process.

      * UCW SDK → Cobo TSS Relay

        23. UCW SDK participates in the signing process by forwarding the transaction approval to the Cobo TSS Relay.

        24. Cobo TSS Relay returns the signature to the UCW SDK.

    * **Update transaction status**

      * Client App → UCW SDK

        25. Client App checks the status of the transaction via the UCW SDK by calling the [Get transactions](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-transactions) operation.

      * UCW SDK → Client App

        26. UCW SDK returns the current transaction status to the Client App.

      * Client App → Client Backend

        27. Client App sends a transaction status update to the Client Backend.

    * **Finalize the transaction**

      * Cobo TSS Relay → Cobo Backend

        28. Cobo TSS Relay sends the final signature to the Cobo Backend.

      * Cobo Backend → Client Backend

        29. You can get the final transaction information on the Client Backend via webhook or polling.

        * **Webhook Option**

          Cobo Backend sends the final transaction information via webhook to the Client Backend.

          <Info>To see the available webhook event types, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types).</Info>

          <Info>To see how to set up your Client Backend to receive webhook events, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).</Info>

        * **Polling option**

          Client Backend polls the Cobo Backend for the final transaction information by calling the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operation.

          Cobo Backend returns the transaction status to the Client Backend.
  </Step>
</Steps>

## 3. Create a transaction

<Steps>
  <Step title="">
    This section details the process of estimating transaction fees, submitting a transaction, and participating in the signing process for a transaction in your User-Controlled Wallets. It outlines the sequence of interactions between the Client App, UCW SDK, Client Backend, Cobo Backend, and Cobo TSS Relay.

    ```mermaid theme={null}
    sequenceDiagram
        autonumber
        participant App as Client App
        participant SDK as UCW SDK
        participant C as Client Backend
        participant P as Cobo Backend
        participant R as Cobo TSS Relay

        App ->> +C: POST /v1/wallets/{wallet_id}/transactions/estimate_fee , {tx_data}
        C ->> +P: POST /v2/transactions/estimate_fee , {wallet_id, tx_data}
        P ->> -C: return {estimate_fee_info}
        C ->> -App: return {estimate_fee_info}

        App ->> App: select fee

        App ->> +C: POST /v1/wallets/{wallet_id}/transactions , {tx_data}
        C ->> +P: POST /v2/transactions/transfer , {tx_request_id, wallet_id, tx_data}
        P ->> C: return {transaction_id, transaction_info}
        C ->> -App: return {tx_request_id, transaction_id}
        P ->> P: cobo risk control
        P ->> +R: POST create_tss_request
        R ->> -P: return 200 OK
        P ->> -C: use [webhook] or [polling] , {transaction_event_type, transaction_info}

        activate App
        alt use push
            C ->> +App: push notification
        else use polling
            App ->> +C: GET /v1/wallets/{wallet_id}/transactions , {status: unfinished, transaction_info}
            C ->> -App: return {transaction_info}
        end

        App ->> +SDK: SDKInstance.GetTransactions, {transaction_id}
        SDK ->> +R: GetTransactions, {transaction_id}
        R ->> -SDK: {transaction_task_info}
        SDK ->> -App: {transaction_info}

        App ->> App: review transaction info
        App ->> +SDK: SDKInstance.ApproveTransactions {transaction_id}
        SDK ->> +R: participate in signing
        R ->> -SDK: {signature}
        App ->> SDK: SDKInstance.GetTransactions, {transaction_id}
        SDK ->> -App: {transaction_info}
        App ->> C: POST /v1/transactions/{transaction_id}/report
        deactivate App

        R ->> +P: {signature}
        P ->> -C: use [webhook] or [polling] , {transaction_event_type, transaction_info}


    ```

    #### Sequence of operations

    * **Estimate transaction fee**

      * Client App → Client Backend

        1. Client App initiates a fee estimation request by sending transaction data to the Client Backend.

      * Client Backend → Cobo Backend

        2. Client Backend forwards the request to the Cobo Backend to estimate the fee for the transaction by calling the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) operation.

      * Cobo Backend → Client Backend

        3. Cobo Backend processes the request and returns the estimated fee information.

      * Client Backend → Client App

        4. Client Backend returns the estimated fee information to the Client App.

      * Client App

        5. User reviews and selects the appropriate fee using the Client App.

    * **Submit transaction**

      * Client App → Client Backend

        6. After selecting the fee, the Client App submits the transaction data to the Client Backend for processing.

      * Client Backend → Cobo Backend

        7. Client Backend forwards the transaction data to the Cobo Backend to initiate the transaction by calling the [Transfer token](/developers/v2/api-references/transactions/transfer-token) operation.

      * Cobo Backend → Client Backend

        8. Cobo Backend processes the request and returns the transaction ID and other transaction information.

      * Client Backend → Client App

        9. Client Backend returns the transaction information to the Client App.

    * **Perform risk controls and TSS request processing**

      * Cobo Backend

        10. Cobo Backend performs internal risk control checks before proceeding with the transaction.

      * Cobo Backend → Cobo TSS Relay

        11. Cobo Backend sends a request to the Cobo TSS Relay to create a TSS request for the transaction.

      * Cobo TSS Relay → Cobo Backend

        12. Cobo TSS Relay confirms the creation of the TSS request with a 200 OK response.

    * **Monitor transaction status on Client Backend**
      * Cobo Backend → Client Backend

        (13) You can monitor the status of the transaction on the Client Backend through either webhook or polling.

        * **Webhook option**

          Cobo Backend sends transaction updates to the Client Backend using webhooks.

          <Info>To see the available webhook event types, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types).</Info>

          <Info>To see how to set up your Client Backend to receive webhook events, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).</Info>

        * **Polling option**

          Client Backend polls the Cobo Backend to get updates on the transaction status by calling the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operation.

          Cobo Backend returns the transaction status to the Client Backend.

    * **(Optional) Monitor transaction status on Client App**

      * Client Backend → Client App

        You can optionally send the transaction status to the Client App through push notifications or polling.

        * **Push notification option**

          14. Client Backend sends a push notification to the Client App with the transaction status.

        * **Polling option**

          15. Client App polls the Client Backend for the transaction status.

          16. Client Backend returns the transaction status to the Client App.

    * **Review and approve the transaction**

      * Client App → UCW SDK

        17. Client App calls the UCW SDK to retrieve detailed transaction information by calling the [Get transactions](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-transactions) operation.

      * UCW SDK → Cobo TSS Relay

        18. UCW SDK forwards the request to the Cobo TSS Relay to retrieve the transaction information.

        19. Cobo TSS Relay returns the transaction information to the UCW SDK.

      * UCW SDK → Client App

        20. UCW SDK returns the transaction information to the Client App.

      * Client App

        21. User reviews the transaction information on the Client App.

      * Client App → UCW SDK

        22. Client App approves the transaction using the UCW SDK by calling the [Approve transactions](/developers/v2/developer-tools/ucw-sdk/ucw-class/approve-transactions) operation, initiating the signing process.

      * UCW SDK → Cobo TSS Relay

        23. UCW SDK participates in the signing process by forwarding the transaction approval to the Cobo TSS Relay.

        24. Cobo TSS Relay returns the signature to the UCW SDK.

    * **Update transaction status**

      * Client App → UCW SDK

        25. Client App checks the status of the transaction via the UCW SDK by calling the [Get transactions](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-transactions) operation.

      * UCW SDK → Client App

        26. UCW SDK returns the current transaction status to the Client App.

      * Client App → Client Backend

        27. Client App sends a transaction status update to the Client Backend.

    * **Finalize the transaction**

      * Cobo TSS Relay → Cobo Backend

        28. Cobo TSS Relay sends the final signature to the Cobo Backend.

      * Cobo Backend → Client Backend

        29. You can get the final transaction information on the Client Backend via webhook or polling.

        * **Webhook Option**

          Cobo Backend sends the final transaction information via webhook to the Client Backend.

          <Info>To see the available webhook event types, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types).</Info>

          <Info>To see how to set up your Client Backend to receive webhook events, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).</Info>

        * **Polling option**

          Client Backend polls the Cobo Backend for the final transaction information by calling the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operation.

          Cobo Backend returns the transaction status to the Client Backend.
  </Step>
</Steps>

## 4. Backup and restore

<Steps>
  <Step title="Back up and restore your key shares with iCloud">
    This section describes the process of exporting encrypted Secrets from one instance of the UCW SDK in a Client App, saving it to an iCloud server, and subsequently importing the Secrets into another instance of the UCW SDK in a different Client App.
    <Info>A Secrets file contains all essential information about the TSS Node, including your TSS Node ID and key shares.</Info>
    The following sequence diagram details the interactions between the two Client Apps, their respective UCW SDK instances, and the iCloud server.

    ```mermaid theme={null}
    sequenceDiagram
        autonumber
        participant App1 as Client App 1
        participant SDK1 as UCW SDK 1
        participant App2 as Client App 2
        participant SDK2 as UCW SDK 2
        participant I as iCloud Server

        App1 ->> +SDK1: Open
        activate App1
        SDK1 ->> -App1: SDKInstance
        App1 ->> +SDK1: SDKInstance.ExportSecrets(passphrase)
        SDK1 ->> -App1: return {encrypted_secrets}
        App1 ->>- I: save {encrypted_secrets} to
        I ->> +App2: load {encrypted_secrets} from
        App2 ->> +SDK2: ImportSecrets(passphrase, encrypted_secrets)
        SDK2 ->> -App2: ok
        deactivate App2

    ```

    #### Sequence of operations

    * **Open UCW SDK 1 in Client App 1**

      * Client App 1 → UCW SDK 1

        1. Client App 1 opens an instance of the UCW SDK 1 by calling the [Create UCW class](/developers/v2/developer-tools/ucw-sdk/ucw-class/create-ucw) operation.

      * UCW SDK 1 → Client App 1

        2. UCW SDK 1 returns an instance of itself to Client App 1, which can now be used to perform further operations.

    * **Export Secrets**

      * Client App 1 → UCW SDK 1

        3. Client App 1 calls the [Export Secrets](/developers/v2/developer-tools/ucw-sdk/ucw-class/export-secrets) operation on the UCW SDK 1 instance, providing a passphrase for encryption.

      * UCW SDK 1 → Client App 1

        4. UCW SDK 1 encrypts the Secrets using the provided passphrase and returns the encrypted Secrets.

    * **Save encrypted Secrets to iCloud**

      * Client App 1 → iCloud Server

        5. Client App 1 saves the encrypted Secrets to iCloud for secure storage.

    * **Load encrypted Secrets from iCloud**

      * iCloud Server → Client App 2

        6. Client App 2 retrieves the encrypted Secrets from iCloud for use in its own UCW SDK 2 instance.

    * **Import Secrets into UCW SDK 2**

      * Client App 2 → UCW SDK 2

        7. Client App 2 calls the [Import Secrets](/developers/v2/developer-tools/ucw-sdk/other-apis/import-secrets) operation and provides the passphrase and the encrypted Secrets, which allows UCW SDK 2 to import the Secrets.

      * UCW SDK 2 → Client App 2

        8. UCW SDK 2 decrypts and imports the Secrets successfully, confirming the operation with Client App 2.
  </Step>

  <Step title="Create a Recovery Group">
    This section outlines the flow for creating a [Recovery Group](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/holder-group-recovery-group) and performing a key generation process using the UCW SDK. The process involves multiple Client Apps, the Client Backend, the Cobo Backend, and the Cobo TSS Relay.

    ```mermaid theme={null}
    sequenceDiagram
        autonumber
        participant App1 as Client App 1
        participant SDK1 as UCW SDK 1
        participant App23 as Client App 2,3
        participant SDK23 as UCW SDK 2,3
        participant C as Client Backend
        participant P as Cobo Backend
        participant R as Cobo TSS Relay

        App23 ->> +SDK23: Init and Open
        activate App23
        SDK23 ->> -App23: SDKInstance
        App23 ->> +SDK23: SDKInstance.GetNodeInfo
        SDK23 ->> -App23: return {tss_node_id}

        App1 ->> App1: input {app2_tss_node_id, app3_tss_node_id}

        App1 ->> C: POST /v1/vaults/{vault_id}/tss/generate_recovery_group , {app1_tss_node_id, app2_tss_node_id, app3_tss_node_id}
        activate C
        C ->> +P: POST /v2/wallets/mpc/vaults/{vault_id}/key_share_holder_groups , {type: recovery_group, key_share_holders}
        P ->> -C: return {key_share_holder_group_id}

        C ->> +P: POST /v2/wallets/mpc/vaults/{vault_id}/tss_requests , {KeyGenFromKeyGroup, main_group_id}
        P ->> C: return {tss_request_id}
        P ->> P: cobo risk control
        P ->> R: POST create_tss_request
        R ->> P: return 200 OK
        P ->> -C: use [webhook] or [polling] , {tss_request_event_type, tss_request_info}
        deactivate C

        activate App1
        alt use push
            C ->> +App1: push notification
        else use polling
            App1 ->> +C: GET /v1/vaults/{vault_id}/tss/requests/{tss_request_id} , {status: unfinished}
            C ->> -App1: return {transaction_info}
        end

        activate App23
        alt use push
            C ->> +App23: push notification
        else use polling
            App23 ->> +C: GET /v1/vaults/{vault_id}/tss/requests/{tss_request_id} , {status: unfinished}
            C ->> -App23: return {transaction_info}
        end

        App1 ->> +SDK1: SDKInstance.GetTSSRequests {tss_request_id}
        SDK1 ->> -App1: {tss_request_info}
        App1 ->> App1: review pending tss_request
        App1 ->> +SDK1: SDKInstance.ApproveTSSRequests {tss_request_id}
        SDK1 ->> SDK1: waiting for others nodes

        App23 ->> +SDK23: SDKInstance.GetTSSRequests {tss_request_id}
        SDK23 ->> -App23: {tss_request_info}
        App23 ->> App23: review pending tss_request
        App23 ->> +SDK23: SDKInstance.ApproveTSSRequests {tss_request_id}
        SDK23 ->> SDK23: waiting for others nodes

        SDK1 ->> +R: participate in key reshare
        SDK23 ->> +R: participate in key reshare

        R ->> -SDK1: {key reshare result}
        R ->> -SDK23: {key reshare result}

        App1 ->> SDK1: SDKInstance.GetTSSRequests
        SDK1 ->> -App1: {tss request status, key reshare result}
        App1 ->> C: /v1/tss_requests/{tss_request_id}/report
        deactivate App1

        App23 ->> SDK23: SDKInstance.GetTSSRequests
        SDK23 ->> -App23: {tss_request_info}
        App23 ->> C: /v1/tss_requests/{tss_request_id}/report
        deactivate App23

        R ->> +P: {key reshare result}
        P ->> -C: use [webhook] or [polling] , {tss_request_event_type, tss_request_info}

    ```

    #### Sequence of operations

    * **Initialize UCW SDKs 2 and 3 in Client Apps 2 and 3**

      * Client Apps 2, 3 → UCW SDK 2, 3

        1. Client Apps 2 and 3 initiate their respective UCW SDKs 2 and 3 instances by calling the [Create UCW class](/developers/v2/developer-tools/ucw-sdk/ucw-class/create-ucw) operation.

      * UCW SDK 2, 3 → Client Apps 2, 3

        2. UCW SDKs 2 and 3 return the UCW SDK 2 and 3 instances to Client Apps 2 and 3.

      * Client Apps 2, 3 → UCW SDK 2, 3

        3. Client Apps 2 and 3 obtain the TSS Node IDs by calling the [Get TSS Node ID](/developers/v2/developer-tools/ucw-sdk/ucwpublic-class/get-tss-node-id) operation.

      * UCW SDK 2, 3 → Client Apps 2, 3

        4. UCW SDKs 2 and 3 return the TSS Node IDs to Client Apps 2 and 3.

    * **Create Recovery Group**

      * Client App 1

        5. User provides Client App 1 with the TSS Node IDs from Client Apps 2 and 3.

      * Client App 1 → Client Backend

        6. Client App 1, after receiving the TSS Node IDs from Client Apps 2 and 3, submits a request to the Client Backend to create a Recovery Group.

      * Client Backend → Cobo Backend

        7. Client Backend forwards the request to the Cobo Backend by calling the [Create key share holder group](/developers/v2/api-references/wallets--mpc-wallets/create-key-share-holder-group) operation, specifying the Recovery Group details and key share holders.

      * Cobo Backend → Client Backend

        8. The Cobo Backend returns the key share holder group ID to the Client Backend.

    * **Initialize key generation request**

      * Client Backend → Cobo Backend

        9. Client Backend submits a request to the Cobo Backend to use the Main Group to create key shares for your Recovery Group by calling the [Create TSS request](/developers/v2/api-references/wallets--mpc-wallets/create-tss-request) operation and specifying `KenGenFromKeyGroup` as the `type`.

      * Cobo Backend → Client Backend

        10. Cobo Backend processes the request and returns a TSS request ID.

      * Cobo Backend

        11. Cobo Backend performs risk controls.

      * Cobo Backend → Cobo TSS Relay

        12. Cobo Backend sends the request to the Cobo TSS Relay.

      * Cobo TSS Relay → Cobo Backend

        13. Cobo TSS Relay confirms the request completion with a 200 OK message.

    * **Monitor TSS request status on Client Backend**

      * Cobo Backend → Client Backend

        14. You can monitor the TSS request status through webhooks or polling.

        * **Webhook option**

          Cobo Backend sends updates to the Client Backend using webhooks.
          <Info>To see the available webhook event types, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types).</Info>

          <Info>To see how to set up your Client Backend to receive webhook events, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).</Info>

        * **Polling option**

          The Client Backend polls the Cobo Backend for the status of the TSS request by calling the [Get TSS request](/developers/v2/api-references/wallets--mpc-wallets/get-tss-request) operation.

          The Cobo Backend returns the TSS request status to Client Backend.

    * **(Optional) Monitor TSS request status on Client Apps 1, 2, and 3**

      * Client Backend → Client Apps 1, 2, and 3

        You can optionally monitor the TSS request status on Client Apps 1, 2, and 3 through either push notification or polling.

        * **Push notification option**

          15. (15 & 18) Client Backend sends a push notification to Client Apps 1, 2, and 3.

        * **Polling option**

          16. (16 & 19) Client Apps 1, 2, and 3 send Client Backend requests for the TSS request status.

          17. (17 & 20) Client Backend sends Client Apps 1, 2, and 3 the TSS request status.

    * **Review and approve TSS requests in Client Apps**

      * Client App 1 → UCW SDK 1

        21. Client App 1 retrieves the pending TSS request by calling the [Get TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests) operation.

      * UCW SDK 1 → Client App 1

        22. UCW SDK 1 returns the TSS request information to Client App 1.

      * Client App 1

        23. User reviews the TSS request information on Client App 1.

      * Client App 1 → UCW SDK 1

        24. After review, Client App 1 approves the TSS request by calling the [Approve TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/approve-tss-requests) operation.

    * UCW SDK 1

      25. UCW SDK 1 waits for the other TSS Nodes (Client Apps 2 and 3) to approve the request.

    * Client Apps 2, 3 → UCW SDK 2, 3

      26. Client Apps 2 and 3 retrieve the pending TSS request by calling the [Get TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests) operation.

    * UCW SDK 2, 3 → Client Apps 2, 3

      27. UCW SDK 2 and 3 return the TSS request information to Client Apps 2 and 3.

    * Client Apps 2, 3

      28. Users review the TSS request information on Client Apps 2 and 3.

    * Client Apps 2, 3 → UCW SDK 2, 3

      29. After review, Client Apps 2 and 3 approve the TSS request by calling the [Approve TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/approve-tss-requests) operation.

    * UCW SDK 2, 3

      30. UCW SDK 2 and 3 wait for other TSS Node (Client App 1) to complete the approval process.

    * **Participate in key generation**

      * UCW SDK 1, 2, 3 → Cobo TSS Relay

        31. (31 & 32) UCW SDKs 1, 2, and 3 participate in the key generation process by interacting with the Cobo TSS Relay.

        32. (33 & 34) The Cobo TSS Relay returns the key generation results to each UCW SDK instance.

    * **Finalize the TSS request for key generation**

      * Client App 1 → UCW SDK 1

        35. Client App 1 retrieves the status of the TSS request by calling the [Get TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests) operation.

      * UCW SDK 1 → Client App 1

        36. UCW SDK returns the TSS request status and key generation result.

      * Client App 1 → Client Backend

        37. Client App 1 sends an update to the Client Backend to inform the TSS request result.

      * Client Apps 2, 3 → UCW SDK 2, 3

        38. Client Apps 2 and 3 retrieve the status of the TSS request by calling the [Get TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests) operation.

      * UCW SDK 2, 3 → Client Apps 2, 3

        39. UCW SDKs 2 and 3 return the TSS request status.

      * Client Apps 2, 3 → Client Backend

        40. Client Apps 2 and 3 send updates to the Client Backend to inform the TSS request status.

      * Cobo TSS Relay → Cobo Backend

        41. Cobo TSS Relay sends the TSS request result to the Cobo Backend.

    * **Monitor the result in Cobo Backend**
      * Cobo Backend → Client Backend

        42. Client Backend receives the key generation result through webhook or polling.

            * **Webhook option**

              Cobo Backend sends the final key generation result via webhook to the Client Backend.

              <Info>To see the available webhook event types, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types).</Info>

              <Info>To see how to set up your Client Backend to receive webhook events, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).</Info>

            * **Polling option**

              Client Backend polls the Cobo Backend to retrieve the final result by calling the [Get TSS request](/developers/v2/api-references/wallets--mpc-wallets/get-tss-request) operation.

              Cobo Backend sends the final result to Client Backend.
  </Step>

  <Step title="Perform recovery from Recovery Group">
    If the key shares have been lost in a Main Group, you can recover the key shares from a Recovery Group. This section describes the process of generating keys from a Recovery Group for a Main Group using the UCW SDK. The flow involves multiple Client Apps, the Client Backend, the Cobo Backend, and the Cobo TSS Relay.

    ```mermaid theme={null}
    sequenceDiagram
      autonumber
      participant App23 as Client App 2,3
      participant SDK23 as UCW SDK 2,3
      participant App4 as Client App 4
      participant SDK4 as UCW SDK 4
      participant C as Client Backend
      participant P as Cobo Backend
      participant R as Cobo TSS Relay

      App4 ->> +SDK4: Init and Open
      activate App4
      SDK4 ->> -App4: SDKInstance
      App4 ->> +SDK4: SDKInstance.GetTSSNodeID
      SDK4 ->> -App4: return {tss_node_id}

      App4 ->> +C: Get /v1/vaults/{vault_id}/tss/groups , {NodeGroup_RECOVERY_GROUP}
      C ->> -App4: return {recovery_groups}

      App4 ->> App4: select recovery_group

      App4 ->> -C: /v1/vaults/{vault_id}/tss/recover_main_group , {recovery_group_id, tss_node_id(main_group)}


      C ->> +P: POST /v1/wallets/mpc/vaults/{vault_id}/key_share_holder_groups , {tss_node_id(main_group)}
      P ->> -C: return {main_group_id}

      C ->> +P: POST /v2/wallets/mpc/vaults/{vault_id}/tss_requests , {recovery_group_id,main_group_id}
      P ->> C: return {tss_request_id}

      P ->> P: cobo risk control
      P ->> R: POST create_tss_request
      R ->> P: return 200 OK
      P ->> -C: POST /webhook , {tss_request_event_type, tss_request_info}

      activate App23
      alt use push
          C ->> +App23: push notification
      else use polling
          App23 ->> +C: GET /v1/vaults/{vault_id}/tss/requests/{tss_request_id} , {status: unfinished}
          C ->> -App23: return {transaction_info}
      end

      activate App4
      alt use push
          C ->> +App4: push notification
      else use polling
          App4 ->> +C: GET /v1/vaults/{vault_id}/tss/requests/{tss_request_id} , {status: unfinished}
          C ->> -App4: return {transaction_info}
      end

      App23 ->> +SDK23: SDKInstance.GetTSSRequests {tss_request_id}
      SDK23 ->> -App23: {tss_request_info}
      App23 ->> App23: review pending tss_request
      App23 ->> +SDK23:SDKInstance.ApproveTSSRequests {tss_request_id}
      SDK23 ->> SDK23: waiting for others nodes

      App4 ->> +SDK4: SDKInstance.GetTSSRequests {tss_request_id}
      SDK4 ->> -App4: {tss_request_info}
      App4 ->> App4: review pending tss_request
      App4 ->> +SDK4: SDKInstance.ApproveTSSRequests {tss_request_id}
      SDK4 ->> SDK4: waiting for others nodes

      SDK23 ->> +R: participate in key reshare
      SDK4 ->> +R: participate in key reshare

      R ->> -SDK23: {key reshare result}
      R ->> -SDK4: {key reshare result}

      App23 ->> SDK23: SDKInstance.GetTSSRequests
      SDK23 ->> -App23: {tss request status, key reshare result}
      App23 ->> C: /v1/tss_requests/{tss_request_id}/report
      deactivate App23

      App4 ->> SDK4: SDKInstance.GetTSSRequests
      SDK4 ->> -App4: {tss_request_info}
      App4 ->> C: /v1/tss_requests/{tss_request_id}/report
      deactivate App4

      R ->> +P: {key reshare result}
      P ->> -C: use [webhook] or [polling] , {tss_request_event_type, tss_request_info}

    ```

    #### Sequence of operations

    * **Initialize UCW SDK 4 in Client App 4**

      * Client App 4 → UCW SDK 4

        1. Client App 4 initiates its UCW SDK instance by calling the [Create UCW class](/developers/v2/developer-tools/ucw-sdk/ucw-class/create-ucw) operation.

      * UCW SDK 4 → Client App 4

        2. UCW SDK 4 returns the UCW SDK 4 instance.

      * Client App 4 → UCW SDK 4

        3. Client App 4 requests the TSS Node ID by calling the [Get TSS Node ID](/developers/v2/developer-tools/ucw-sdk/ucwpublic-class/get-tss-node-id) operation.

      * UCW SDK 4 → Client App 4

        4. UCW SDK 4 returns the TSS Node ID.

    * **Fetch Recovery Groups**

      * Client App 4 → Client Backend

        5. Client App 4 requests the available Recovery Groups from the Client Backend.

      * Client Backend → Client App 4

        6. Client Backend returns the available Recovery Groups.

    * **Select and submit a Recovery Group**

      * Client App 4

        7. User selects a Recovery Group to use.

      * Client App 4 → Client Backend

        8. After selecting a Recovery Group, Client App 4 submits a request to the Client Backend to recover the Main Group.

      * Client Backend → Cobo Backend

        9. Client Backend forwards the request to the Cobo Backend by calling the [Create key share holder group](/developers/v2/api-references/wallets--mpc-wallets/create-key-share-holder-group) operation and creating a Main Group.

      * Cobo Backend → Client Backend

        10. Cobo Backend returns the Main Group ID.

      * Client Backend → Cobo Backend

        11. Client Backend submits a request to the Cobo Backend to initiate a key generation request by calling the [Create TSS requests](/developers/v2/api-references/wallets--mpc-wallets/create-tss-request) operation and specifying `Recovery` as the `type`.

      * Cobo Backend → Client Backend

        12. Cobo Backend returns the TSS request ID.

      * Cobo Backend

        13. Cobo Backend executes risk controls.

      * Cobo Backend → Cobo TSS Relay

        14. Cobo Backend forwards the request to the Cobo TSS Relay.

      * Cobo TSS Relay → Cobo Backend

        15. Cobo TSS Relay confirms the request with a 200 OK message.

    * **Monitor TSS request status on Client Backend**

      * Cobo Backend → Client Backend

        16. Client Backend monitors the TSS request status through webhooks or polling.

            * **Webhook option**

              Cobo Backend sends a webhook to notify the Client Backend of the TSS request status.

              <Info>To see the available webhook event types, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types).</Info>

              <Info>To see how to set up your Client Backend to receive webhook events, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).</Info>

            * **Polling option**

              Client Backend polls the TSS request status by calling the [Get TSS request](/developers/v2/api-references/wallets--mpc-wallets/get-tss-request) operation.

              Cobo Backend sends the TSS request status to Client Backend.

    * **(Optional) Monitor TSS request status on Client Apps 2, 3, and 4**

      * Client Backend → Client Apps 2, 3, and 4

        You can optionally monitor the TSS request status on Client Apps 2, 3, and 4 through push notifications or polling.

        * **Push notification option**

          17. (17 & 20) Client Backend sends TSS request status through push notifications to Client Apps 2, 3, and 4.

        * **Polling option**

          18. (18 & 21) Client Apps 2, 3, and 4 send a request to Client Backend requesting the TSS request status.

          19. (19 & 22) Client Backend returns the TSS request status to Client Apps 2, 3, and 4.

    * **Review and approve TSS requests**

      * Client App 2, 3 → UCW SDK 2, 3

        23. Client Apps 2 and 3 retrieve the pending TSS request by calling the [Get TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests) operation.

      * UCW SDK 2, 3 → Client App 2, 3

        24. UCW SDK 2 and 3 return the TSS request information.

      * Client App 2, 3

        25. Users review the TSS request on Client Apps 2 and 3.

      * Client App 2, 3 → UCW SDK 2, 3

        26. After reviewing the request, Client Apps 2 and 3 approve it by calling the [Approve TSS request](/developers/v2/developer-tools/ucw-sdk/ucw-class/approve-tss-requests) operation.

      * UCW SDK 2, 3

        27. UCW SDK 2 and 3 wait for other TSS Nodes to complete their approval process.

      * Client App 4 → UCW SDK 4

        28. Client Apps 4 retrieves the pending TSS request by calling the [Get TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests) operation.

      * UCW SDK 4 → Client App 4

        29. UCW SDK 4 returns the TSS request information.

      * Client App 4

        30. User reviews the pending TSS request on Client Apps 4.

      * Client App 4 → UCW SDK 4

        31. After reviewing the request, Client App 4 approves it by calling the [Approve TSS request](/developers/v2/developer-tools/ucw-sdk/ucw-class/approve-tss-requests) operation.

      * UCW SDK 4

        32. UCW SDK 4 waits for other TSS Nodes to complete their approval process.

    * **Participate in key generation**

      * UCW SDK 2, 3, 4 → Cobo TSS Relay

        33. (33 & 34) UCW SDKs 2, 3, and 4 participate in the key generation process by communicating with the Cobo TSS Relay.

      * Cobo TSS Relay → UCW SDK 2, 3, 4

        35. (35 & 36) The Cobo TSS Relay returns the key generation results to each UCW SDK instance.

    * **Finalize the TSS request**

      * Client Apps 2, 3, 4 → UCW SDK 2, 3, 4

        37. (37 & 40) Client Apps 2, 3, and 4 retrieve the TSS request status by calling the [Get TSS request](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests) operation.

      * UCW SDK 2, 3, 4 → Client Apps 2, 3, 4

        38. (38 & 41) UCW SDK 2, 3, and 4 return the TSS request status to Client Apps 2, 3, and 4.

      * Client Apps 2, 3, 4 → Client Backend

        39. (39 & 42) After receiving the TSS request result, Client Apps 2, 3, and 4 send updates to the Client Backend.

      * Cobo TSS Relay → Cobo Backend

        43. The Cobo TSS Relay sends the final key generation result to the Cobo Backend.

    * **Monitor the result in Cobo Backend**

      * Cobo Backend → Client Backend

        44. Client Backend receives TSS request result through webhooks or polling.

            * **Webhook option**

              Cobo Backend sends the final key generation result via webhooks.

              <Info>To see the available webhook event types, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types).</Info>

              <Info>To see how to set up your Client Backend to receive webhook events, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).</Info>

            * **Polling option**

              Client Backend polls the final key generation result by calling the [Get TSS requests](/developers/v2/api-references/wallets--mpc-wallets/get-tss-request) operation.

              Cobo Backend sends Client Backend the key generation result.
  </Step>

  <Step title="Perform disaster recovery">
    In the unlikely event that Cobo is no longer in service, you can reconstruct the [root extended private key](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/object-model#root-extended-private-key) that corresponds to your User-Controlled Wallets. All child private keys that correspond to the wallet addresses in this User-Controlled Wallets can then be derived from this root extended private key. The flow involves multiple Client Apps, UCW SDKs, and the Client Backend.

    ```mermaid theme={null}
    sequenceDiagram
        autonumber
        participant App2 as Client App 2
        participant SDK2 as UCW SDK 2
        participant App3 as Client App 3
        participant SDK3 as UCW SDK 3
        participant C as Client Backend

        App2 ->> +C: GET /vaults/{vault_id}/disaster_recovery
        activate App2
        C ->> -App2: return {addresses, path}
        deactivate App2

        App3 ->> +SDK3: Open
        activate App3
        SDK3 ->> -App3: SDKInstance
        App3 ->> +SDK3: SDKInstance.ExportRecoveryKeyShares(tss_key_share_group_id, passphrase)
        SDK3 ->> -App3: return {sdk3_json_recovery_groups}
        deactivate App3

        App2 ->> +SDK2: Open
        activate App2
        SDK2 ->> -App2: SDKInstance
        App2 ->> +SDK2: SDKInstance.ExportRecoveryKeyShares(tss_key_share_group_id, passphrase)
        SDK2 ->> -App2: return {sdk2_json_recovery_groups}
        deactivate App2

        App2 ->> +SDK2: Open: UCWRecoverKey
        activate App2
        SDK2 ->> -App2: UCWRecoverKeyInstance
        App2 ->> +SDK2: UCWRecoverKeyInstance.ImportRecoveryKeyShare(sdk2_json_recovery_groups, passphrase)
        SDK2 ->> -App2: return success
        App2 ->> +SDK2: UCWRecoverKeyInstance.ImportRecoveryKeyShare(sdk3_json_recovery_groups, passphrase)
        SDK2 ->> -App2: return success
        App2 ->> +SDK2: UCWRecoverKeyInstance.RecoverPrivateKeys(addresses_info)
        SDK2 ->> App2: return {root_private_keys, child_private_keys}
        deactivate App2

    ```

    #### Sequence of operations

    * **Fetch disaster recovery addresses**

      * Client App 2 → Client Backend

        1. Client App 2 requests disaster recovery information from the Client Backend.

      * Client Backend → Client App 2

        2. Client Backend returns the relevant addresses and path for disaster recovery.

    * **Export key shares of Client App 3**

      * Client App 3 → UCW SDK 3

        3. Client App 3 opens its UCW SDK 3 instance by calling the [Create UCW class](/developers/v2/developer-tools/ucw-sdk/ucw-class/create-ucw) operation.

      * UCW SDK 3 → Client App 3

        4. UCW SDK 3 returns the UCW SDK 3 instance.

      * Client App 3 → UCW SDK 3

        5. Client App 3 exports its recovery key shares using a passphrase for encryption by calling the [Export recovery key shares](/developers/v2/developer-tools/ucw-sdk/ucw-class/export-recovery-key-shares) operation.

      * UCW SDK 3 → Client App 3

        6. UCW SDK 3 returns the passphrase-encrypted JSON data of key shares.

    * **Export key shares of Client App 2**

      * Client App 2 → UCW SDK 2

        7. Client App 2 opens its UCW SDK 2 instance by calling the [Create UCW class](/developers/v2/developer-tools/ucw-sdk/ucw-class/create-ucw) operation.

      * UCW SDK 2 → Client App 2

        8. UCW SDK 2 returns the UCW SDK 2 instance.

      * Client App 2 → UCW SDK 2

        9. Client App 2 exports its recovery key shares using a passphrase for encryption by calling the [Export recovery key shares](/developers/v2/developer-tools/ucw-sdk/ucw-class/export-recovery-key-shares) operation.

      * UCW SDK 2 → Client App 2

        10. UCW SDK 2 returns the passphrase-encrypted JSON data of key shares.

    * **Initiate key recovery in Client App 2**

      * Client App 2 → UCW SDK 2

        11. Client App 2 opens a UCWRecoverKey instance in UCW SDK 2 by calling the [Create UCW recover key](/developers/v2/developer-tools/ucw-sdk/ucwrecoverkey-class/create-ucw-recover-key) operation.

      * UCW SDK 2 → Client App 2

        12. UCW SDK 2 returns the UCWRecoverKey instance.

    * **Import key shares from Client Apps 2 and 3**

      * Client App 2 → UCW SDK 2

        13. Client App 2 imports the recovery key shares from UCW SDK 2's exported passphrase-encrypted JSON data of key shares by calling the [Import recovery key share](/developers/v2/developer-tools/ucw-sdk/ucwrecoverkey-class/import-recovery-key-share) operation and passing in UCW SDK 2's exported passphrase-encrypted JSON data of key shares.

      * UCW SDK 2 → Client App 2

        14. UCW SDK 2 returns success.

      * Client App 2 → UCW SDK 3

        15. Client App 2 imports the recovery key shares from UCW SDK 3's exported passphrase-encrypted JSON data of key shares by calling the [Import recovery key share](/developers/v2/developer-tools/ucw-sdk/ucwrecoverkey-class/import-recovery-key-share) operation and passing in UCW SDK 3's exported passphrase-encrypted JSON data of key shares

      * UCW SDK 2 → Client App 2

        16. UCW SDK 2 returns success.

    * **Recover the root extended private key**

      * Client App 2 → UCW SDK 2

        17. After importing the key shares, Client App 2 initiates the recovery of the full root extended private key for the specified address by calling the [Recovery private key](/developers/v2/developer-tools/ucw-sdk/ucwrecoverkey-class/recover-private-keys) operation.

      * UCW SDK 2 → Client App 2

        18. UCW SDK 2 returns the root extended private key and its child private keys.
  </Step>
</Steps>


# Appendix
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/appendix

Appendix for the Server Co-signer guide.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## Configure the TSS Node

Currently, you can configure the TSS Node in two methods:

* Through the configuration file.
* Through command line arguments, for example, `./tss-node.sh start --ws-url=ws://ws.example.com/ws`.

It's recommended that you use the configuration file to configure the TSS Node. To do so, please follow these steps:

1. Navigate to the `configs` directory.
2. Copy and paste the file `cobo-tss-node-config.yaml.template`.
3. Rename the copied file to `cobo-tss-node-config.yaml`. The directory structure will appear as follows:

   ```
   cobo-tss-node-generic

   ├── configs

   │ ├── cobo-tss-node-config.yaml

   │ └── cobo-tss-node-config.yaml.template (default configuration file template)

   └── tss-node.sh (startup script)
   ```
4. Edit the `cobo-tss-node-config.yaml` file:
   1. Open the configuration file in a text editor.
   2. Review all configuration items in the file. Most items have reasonable default values, so you only need to modify specific items based on your actual needs. You can refer to [Configuration items](#configuration-items) to understand the meaning of key configuration items.
   3. Modify necessary items according to your environment. For example:
      * Set `env` to `production` for production environment
      * Configure the `callback` section to set up the TSS Node Callback server
      * Adjust log configurations as needed
   4. Save changes and close the file.

### Configuration items

| **Configuration Item**        | **Description**                                                                                                                                                                                 |
| ----------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| env                           | The operating environment. Can be either `development` or `production`. For details, see [Environments](/developers/v2/guides/overview/environments).                                                      |
| db.path                       | The path to the database file. You should NEVER modify this file.                                                                                                                               |
| callback                      | Configurations for the TSS Node callback servers. For details, see [Configure TSS Node settings](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-configure#configure-tss-node-settings) |
| log.std.enable                | Whether to output terminal log.                                                                                                                                                                 |
| log.std.level                 | Log level to output to the terminal. Can be one of: `error`, `warn`, `info`, or `debug`.                                                                                                        |
| log.file.enable               | Whether to save the log file.                                                                                                                                                                   |
| log.file.level                | Log level to export to the log file.                                                                                                                                                            |
| log.file.filename             | Path to the log file.                                                                                                                                                                           |
| log.file.maxsize              | Maximum size of the log file.                                                                                                                                                                   |
| log.file.max\_backups         | Number of backups for each log file.                                                                                                                                                            |
| metrics.job                   | Global tag for all metrics. Default value is "tss-node".                                                                                                                                        |
| metrics.instance              | Global tag to identify the instance number. Default value is 0.                                                                                                                                 |
| metrics.name\_prefix          | Prefix added to all metric names.                                                                                                                                                               |
| metrics.influxdb.server\_addr | The address of your InfluxDB server (e.g., [http://example.com:8086](http://example.com:8086)).                                                                                                 |
| metrics.influxdb.database     | The name of your InfluxDB database.                                                                                                                                                             |
| metrics.influxdb.username     | Username for InfluxDB authentication.                                                                                                                                                           |
| metrics.influxdb.password     | Password for InfluxDB authentication.                                                                                                                                                           |

## TSS Node commands

### init

```
sudo ./tss-node.sh init
```

You can initialize the TSS Node and create a database file. The execution will fail if the database file already exists. For more information, please refer to [Initialize the TSS Node](/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-deployment#initialize-the-tss-node).

### info

```
sudo ./tss-node.sh info
```

You can review the information associated with the TSS Node, including the TSS Node ID and the TSS Node's callback public key used to communicate with the TSS Node callback server.

The output example is as follows.

```
$ sudo ./tss-node.sh info

Container started: 5c3819f6bf9425312ad5fe9561a9d8a4ae7145e05f73b3998a3a8112d7056653

Wait a few seconds ..

INFO[2022-12-14T09:12:11Z] Node ID: coboXNCDGc4eWaWYTbbgH3Q5jmNNRpZzVatRXyanYeC2XjkJb

INFO[2022-12-14T09:12:11Z] Callback public key:

-----BEGIN PUBLIC KEY-----

MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAz13MMDtCMdmBci/f7boS

……

gQIDAQAB

-----END PUBLIC KEY-----

5c3819f6bf9425312ad5fe9561a9d8a4ae7145e05f73b3998a3a8112d7056653
```

### info group

```
sudo ./tss-node.sh info group [group_id]
```

You can use the `info group` command to query the information of the corresponding key share holder group.:

| **Item**                 | **Value**                               | **Description**                                                                                               |
| ------------------------ | --------------------------------------- | ------------------------------------------------------------------------------------------------------------- |
| Group ID                 | vnJShriEOIzBLaOUxUDs                    | Unique identifier of a key share holder group.                                                                |
| Created Time             | 2023-01-11 14:36:42.179778596 +0000 UTC | Creation time of the key share holder group.                                                                  |
| Root Extended Public Key | xpub661MyMwAq……Mcet8                    | The root extended public key that corresponds to the key shares under the current group.                      |
| ChainCode                | 0x098a……9dd9                            | The chain code corresponding to the root extended public key, in hexadecimal format.                          |
| Share ID                 | 121637……483926                          | The ID of the key share, in decimal format.                                                                   |
| Share Public Key         | 0x0231adf……d2773                        | The public key that corresponds to the key share. Default value: compressed public key in hexadecimal format. |
| Type                     | 1                                       | Type: 1 represents ECDSA, and 2 represents EdDSA.                                                             |
| Curve                    | secp256k1                               | Supported signature algorithm.                                                                                |
| Threshold                | 2                                       | The minimum number of key shares required for each transaction signing.                                       |
| Local Node ID            | coboA1B2C3D4                            | The Node ID of the locally stored TSS Node.                                                                   |
| Other Node IDs           | \[coboA1B2C3D4, coboA2B3C4D5]           | The Node ID of the TSS Node managed by other parties.                                                         |
| Participants:            | 3                                       | The total number of key shares, Node IDs, and key share IDs.                                                  |

### start

```
sudo ./tss-node.sh start
```

The cobo-tss-node will start running.

### version

```
sudo ./tss-node.sh version
```

You can use the `version` command to query the version of the TSS Node.

### status

```
sudo ./tss-node.sh status
```

You can use the `status` command to query the status of the TSS Node. An example output is as follows:

```
$ sudo ./tss-node.sh status

Checking docker engine ... OK, version: 19.03.6

Checking container image ... OK, id: sha256:4ff66478be3f193293fbaf85ce764734dab14eff002699636d1329a16f1ce57b

=================================================================

Recent logs from TSS-node daemon container cefc3335c10b (Running)

-----------------------------------------------------------------

INFO[2022-12-14T09:00:37Z] Failed to register service: invalid TSS Node, please initial TSS Node on Cobo MPC Server first

INFO[2022-12-14T09:00:52Z] Start to register service

INFO[2022-12-14T09:00:52Z] Failed to register service: invalid TSS Node,please initial TSS Node on Cobo MPC Server first

INFO[2022-12-14T09:01:07Z] Start to register service

INFO[2022-12-14T09:01:07Z] Failed to register service: invalid TSS Node, please initial TSS Node on Cobo MPC Server first
```

Execution workflow:

* Verify the successful installation of Docker Engine and ensure the client has the necessary permissions.
* Check the status of the SGX driver (applicable to an SGX-ready version).
* Confirm the existence of the built container image.
* Inspect containers for any errors.
* Monitor the currently running TSS Node container and display the latest five logs.

### log

```
sudo ./tss-node.sh log
```

Use this command to view the logs of the currently running TSS Node container.

### stop

```
sudo ./tss-node.sh stop
```

Use this command to stop the currently running TSS Node container.


# Configure callback keys and TSS Node
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-configure

Configure callback keys and TSS Node settings for secure communication between your callback server and TSS Node

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This guide explains how to configure secure communication between your callback server and TSS Node using RSA key pairs.

## Generate and exchange callback keys

### 1. Generate callback server keys

On your callback server, generate an RSA key pair:

1. Generate a private key:

```bash theme={null}
openssl genrsa -out callback-server-pri.pem 4096
```

2. Configure the private key on the callback server because you will need to use it to sign the callback response.

3. Export the public key:

```bash theme={null}
openssl rsa -in callback-server-pri.pem -pubout >callback-server-pub.key
```

### 2. Get the TSS Node's callback public key

After initializing your TSS Node, retrieve its callback public key:

```bash theme={null}
sudo ./tss-node.sh info
```

The output will include the callback public key:

```
INFO[2022-12-14T07:09:44Z] Callback public key:
-----BEGIN PUBLIC KEY-----
MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEA4ki4fHY4/oSJOYBxBUI1
...
s8wADQvpbJTyPkkMyq/i5SkCAwEAAQ==
-----END PUBLIC KEY-----
```

### 3. Exchange public keys

1. Copy your callback server's public key to your TSS Node's installation directory, such as:

```
cobo-tss-node-generic
├── configs
│   ├── callback-server-pub.key
│   └── cobo-tss-node-config.yaml
```

2. Copy the TSS Node's callback public key to your callback server's configuration

## Configure TSS Node settings

Modify the `cobo-tss-node-config.yaml` file on your TSS Node to include the callback server's URL, public key, and other callback-related settings.

You can configure multiple callback servers for enhanced security. The TSS Node will only execute a task if all configured callback servers approve it. The following example shows how to configure if you have two callback servers:

```yaml theme={null}
callback:
  cb_server_v2:
    - service_address: https://<CALLBACK_SERVER_URL_1>/v2/check
      pubkey_path: configs/customer-callback-server-pub-01.key
    - service_address: https://<CALLBACK_SERVER_URL_2>/v2/check
      pubkey_path: configs/customer-callback-server-pub-02.key
  token_expire_minutes: 2
  retry_times: 60
  sleep_seconds: 60
  request_timeout: 10
  monitor_interval: 1h
```

### Configuration parameters

* `cb_server`: A list of addresses of the TSS Node callback servers that receive the [v1 version](/developers/v1/overview/mpc-wallet/callback/callback-server-requirements/keygen-request) of the callback request.  While still supported, we strongly recommend using the `cb_server_v2` option instead, as it provides more comprehensive request information and is more compatible with the WaaS 2.0 API.
* `cb_server_v2`: A list of addresses of the TSS Node callback servers that receive the v2 version of the callback request.
  * `service_address`: HTTP endpoint of your callback server.
  * `pubkey_path`: Path to your callback server's public key file.
* `token_expire_minutes`: JWT expiration time in minutes.
* `retry_times`: Maximum number of retry attempts for failed requests.
* `sleep_seconds`: Delay between retry attempts in seconds.
* `request_timeout`: Timeout duration for HTTP requests in seconds. Specifies how long the TSS Node waits for a response from the callback server before considering the request timed out.
* `monitor_interval`: Specifies how often the TSS Node checks the callback server's status. Use `s` for seconds, `m` for minutes, or `h` for hours (e.g., `30s`, `5m`, `2h`). If omitted, status monitoring is disabled.

## Verify configuration

After configuring both servers:

1. Start your callback server
2. Start your TSS Node
3. Test the connection by initiating a task request
4. Verify the callback flow

## Next steps

* [Back up your key shares](/developers/v2/guides/mpc-wallets/server-co-signer/key-shares-backup)
* [Learn about embedded risk control mechanism](/developers/v2/guides/mpc-wallets/server-co-signer/embedded-risk-controls)


# Callback request and response formats
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-data-structure

Detailed specifications of the payload formats used in TSS Node callback server interaction

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This document specifies the request and response payload formats used in TSS Node callback server communication.

## Callback request

The callback request is sent from the TSS Node to the callback server.

### Base request structure

| Field           | Type     | Description                                                                                                                                                                                                                                                                                      |
| --------------- | -------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| request\_id     | `string` | The unique ID of the callback request.                                                                                                                                                                                                                                                           |
| request\_type   | `int`    | Type of the callback request:<br />- `TypePing` (0): Used for heartbeat monitoring<br />- `TypeKeyGen` (1): Creating new key shares for your MPC Wallets.<br />- `TypeKeySign` (2): Signing transactions or messages.<br />- `TypeKeyReshare` (3): Redistributing key shares among participants. |
| request\_detail | `string` | Details specific to the request type. The structure varies depending on the request type. The content is a JSON-serialized string.                                                                                                                                                               |
| extra\_info     | `string` | Additional contextual information. The structure varies depending on the request type. The content is a JSON-serialized string.                                                                                                                                                                  |

### TypePing request

Used for heartbeat monitoring of the callback server.

If you have specified the `monitor_interval` parameter when [configuring the TSS Node settings](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-configure#configure-tss-node-settings), the node will periodically send the request to verify server availability.

```yaml theme={null}
callback:
  monitor_interval: 1h # Monitoring interval; if empty, monitoring is disabled
```

For `TypePing` requests, `request_id`, `request_detail` and `extra_info` will be empty objects.

### TypeKeyGen request

Used for key share generation.

#### request\_detail

| Field         | Type            | Description                                                                                                       |
| ------------- | --------------- | ----------------------------------------------------------------------------------------------------------------- |
| threshold     | `int`           | The number of key share holders required to approve operations in this key share holder group.                    |
| node\_ids     | `array[string]` | The TSS Node IDs of the key share holders in this key share holder group.                                         |
| curve         | `int`           | The elliptic curve type of the root extended public key. Possible values: <br />`0`: Secp256k1<br />`2`: Ed25519. |
| task\_id      | `string`        | The unique identifier for this key generation task.                                                               |
| biz\_task\_id | `string`        | For this request type, this field contains the TSS request ID.                                                    |

#### extra\_info

| Field                             | Type     | Description                                                                                                                                                                                                                                            |
| --------------------------------- | -------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| org                               | `object` | The organization information:<br />- `org_id`: String. The ID of the organization.<br />- `name`: String. The organization name.<br />- `created_timestamp`: Int. The organization's creation time in Unix timestamp format, measured in milliseconds. |
| project                           | `object` | The project information. For details, see the response of the [Get project information](/developers/v2/api-references/wallets--mpc-wallets/get-project-information) operation.                                                                                    |
| vault                             | `object` | The vault information. For details, see the response of the [Get vault information](/developers/v2/api-references/wallets--mpc-wallets/get-vault-information) operation.                                                                                          |
| target\_key\_share\_holder\_group | `object` | The key share holder group information. For details, see the response of the [Get key share holder group information](/developers/v2/api-references/wallets--mpc-wallets/get-key-share-holder-group-information) operation.                                       |
| tss\_request                      | `object` | The TSS request information. For details, see the response of the  [Get TSS request](/developers/v2/api-references/wallets--mpc-wallets/get-tss-request) operation.                                                                                               |

### TypeKeySign request

Used for transaction or message signing operations.

#### request\_detail

| Field             | Type            | Description                                                                                                                               |
| ----------------- | --------------- | ----------------------------------------------------------------------------------------------------------------------------------------- |
| group\_id         | `string`        | The ID of the TSS key share group.                                                                                                        |
| root\_pub\_key    | `string`        | The root extended public key of the group.                                                                                                |
| used\_node\_ids   | `array[string]` | The list of TSS Node IDs participating in signing.                                                                                        |
| bip32\_path\_list | `array[string]` | The BIP32 derivation paths.                                                                                                               |
| msg\_hash\_list   | `array[string]` | The list of message hashes to sign.                                                                                                       |
| tweak\_list       | `array[string]` | The list of tweaks to apply.                                                                                                              |
| signature\_type   | `int`           | The type of signature to generate. Possible values:<br />- `1`: ECDSA signature<br />- `2`: EdDSA signature<br />- `3`: Schnorr signature |
| tss\_protocol     | `int`           | The TSS protocol. Possible values:<br />- `1`: GG18<br />- `2`: Lindell<br />- `3`: EddsaTSS                                              |
| task\_id          | `string`        | The unique identifier for this signing task.                                                                                              |
| biz\_task\_id     | `string`        | For this request type, this field contains the transaction ID.                                                                            |

#### extra\_info

| Field                             | Type            | Description                                                                                                                                                                                                                                            |
| --------------------------------- | --------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| org                               | `object`        | The organization information:<br />- `org_id`: String. The ID of the organization.<br />- `name`: String. The organization name.<br />- `created_timestamp`: Int. The organization's creation time in Unix timestamp format, measured in milliseconds. |
| project                           | `object`        | The project information. For details, see the response of the [Get project information](/developers/v2/api-references/wallets--mpc-wallets/get-project-information) operation.                                                                                    |
| vault                             | `object`        | The vault information. For details, see the response of the [Get vault information](/developers/v2/api-references/wallets--mpc-wallets/get-vault-information) operation.                                                                                          |
| wallet                            | `object`        | The wallet information. For details, see the response of the [Get wallet information](/developers/v2/api-references/wallets/get-wallet-information) operation.                                                                                                    |
| signer\_key\_share\_holder\_group | `object`        | The information of the key share holder group that signs the transaction. For details, see the response of the [Get key share holder group information](/developers/v2/api-references/wallets--mpc-wallets/get-key-share-holder-group-information) operation.     |
| source\_addresses                 | `array[object]` | The information of the source addresses of the transaction. For details, see the response of the [List wallet addresses](/developers/v2/api-references/wallets/list-wallet-addresses) operation.                                                                  |
| transaction                       | `object`        | The information of the transaction to sign. For details, see the response of the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operation.                                                                 |

<Note>
  The `transaction` object includes an `initiator_type` field that identifies how the transaction was initiated, so your callback server can distinguish, for example, an API-initiated transaction from an App-initiated one. Possible values are `API` (initiated through the WaaS API), `Web` (initiated from Cobo Portal), `App` (initiated from Cobo Portal Apps), and `External` (initiated outside Cobo). For the full transaction schema, see the response of the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operation.
</Note>

### TypeKeyReshare request

Used for [key resharing](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/manage-key-share-groups#manage-recovery-groups) operations. Resharing means to use an existing key share holder group to generate key shares for a new group.

#### request\_detail

| Field           | Type            | Description                                                                                      |
| --------------- | --------------- | ------------------------------------------------------------------------------------------------ |
| old\_group\_id  | `string`        | The ID of the existing TSS key share group.                                                      |
| root\_pub\_key  | `string`        | The root extended public key of the vault.                                                       |
| curve           | `int`           | The elliptic curve type of the root extended public key. <br />`0`: Secp256k1<br />`2`: Ed25519. |
| used\_node\_ids | `array[string]` | The TSS Node IDs of the existing key share holder group.                                         |
| old\_threshold  | `int`           | The threshold value of the existing key share holder group used.                                 |
| new\_threshold  | `int`           | The threshold value of the new key share holder group.                                           |
| new\_node\_ids  | `array[string]` | The TSS Node IDs of the new key share holder group.                                              |
| task\_id        | `string`        | The unique identifier for this resharing task.                                                   |
| biz\_task\_id   | `string`        | For this request type, this field contains the TSS request ID.                                   |

#### extra\_info

| Field                             | Type     | Description                                                                                                                                                                                                                                            |
| --------------------------------- | -------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| org                               | `object` | The organization information:<br />- `org_id`: String. The ID of the organization.<br />- `name`: String. The organization name.<br />- `created_timestamp`: Int. The organization's creation time in Unix timestamp format, measured in milliseconds. |
| project                           | `object` | The project information. For details, see the response of the [Get project information](/developers/v2/api-references/wallets--mpc-wallets/get-project-information) operation.                                                                                    |
| vault                             | `object` | The vault information. For details, see the response of the [Get vault information](/developers/v2/api-references/wallets--mpc-wallets/get-vault-information) operation.                                                                                          |
| source\_key\_share\_holder\_group | `object` | The information of the existing key share holder group. For details, see the response of the [Get key share holder group information](/developers/v2/api-references/wallets--mpc-wallets/get-key-share-holder-group-information) operation.                       |
| target\_key\_share\_holder\_group | `object` | The information of the new key share holder group. For details, see the response of the [Get key share holder group information](/developers/v2/api-references/wallets--mpc-wallets/get-key-share-holder-group-information) operation.                            |
| tss\_request                      | `object` | The TSS request information. For details, see the response of the  [Get TSS request](/developers/v2/api-references/wallets--mpc-wallets/get-tss-request) operation.                                                                                               |

## Callback response

Your callback server must respond to all callback requests with the following structure:

| Field       | Type     | Description                                                                                                                                                                                                        |
| ----------- | -------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| status      | `int`    | The response status code. `0` indicates success. Any other value indicates that an error occurred while processing the request in the callback server.                                                             |
| request\_id | `string` | The unique ID of the callback request.                                                                                                                                                                             |
| action      | `string` | Action to take. Possible values:<br />- `APPROVE`: Approve the request and proceed with the operation<br />- `REJECT`: Deny the request and stop the operation                                                     |
| error       | `string` | The error message:<br />- When `status` is not `0`: Contains internal error messages from the callback server.<br />- When `status` is `0` and action is `REJECT`: Contains the specific reason for the rejection. |

### HTTP response requirements

The callback response described above is the JSON body of the HTTP response. Return your response with an HTTP `200` (OK) status code, and set the body `status` field to `0` to indicate that your callback server processed the callback successfully.

The HTTP status code and the body `status` field are different. The HTTP status code reports whether the HTTP request reached and was handled by your callback server, while the body `status` field reports the result of processing the callback: a value of `0` indicates success, and any other value indicates that an error occurred in the callback server while processing the request.

#### Example

```json theme={null}
// Callback request (TypeKeySign) from the TSS Node
{
  "request_id": "f1e2d3c4b5a6",
  "request_type": 2,
  "request_detail": "{...}",
  "extra_info": "{...}"
}
```

```json theme={null}
// Callback response (HTTP status code 200)
{
  "status": 0,
  "request_id": "f1e2d3c4b5a6",
  "action": "APPROVE",
  "error": ""
}
```

### Important notes

* If the TSS Node fails to receive an HTTP response, it will retry the callback request.
* After exceeding the maximum retry attempts, the risk control result will be set to `REJECT`.
* For `TypePing` requests, a successful response (body `status` `0`) indicates that your callback server is available.


# Deploy a TSS Node callback server
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-deploy

Step-by-step guide to deploy a TSS Node callback server

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This guide explains how to deploy your TSS Node callback server.

## Sample callback server

Cobo provides example callback server implementations in multiple programming languages to help you quickly develop your callback server. You can find these examples in our [GitHub repository](https://github.com/CoboGlobal/cobo-mpc-callback-server-v2-template).

## General workflow

Your callback server must:

1. Implement HTTP endpoints for receiving task requests
2. Process JWT-signed messages from the TSS Node
3. Implement your custom risk control logic
4. Return signed responses to the TSS Node

### HTTP endpoint

The callback server must expose an HTTP endpoint with these specifications:

* Path: `/v2/check` (or any other path that aligns with your business needs)
  <Note>Remember to register your chosen path in the TSS Node's configuration file. For detailed instructions, refer to [Configure TSS Node settings](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-configure#configure-tss-node-settings).</Note>
* Method: `POST`
* Content-Type: `application/x-www-form-urlencoded`

### Parsing the request

For each task request, the TSS Node:

1. Creates a `CallbackRequest` struct based on the task type (KeyGen, KeySign, or KeyReshare)
2. Serializes the `CallbackRequest` struct to JSON format to obtain `CallbackRequestJsonString`
3. Uses `CallbackRequestJsonString` as the JWT payload and signs it with its RSA private key (the TSS Node's callback private key)
4. Sends an HTTP POST request with the JWT in a form field named `TSS_JWT_MSG`

Your callback server must:

1. Extract the JWT from the `TSS_JWT_MSG` form field in the HTTP POST request
2. Verify the JWT signature using the TSS Node's callback public key
3. Extract the payload from the JWT and deserialize it into a `CallbackRequest` struct
4. Based on the `CallbackRequest` type, deserialize the `meta` field to obtain detailed request information

### Risk control implementation

Your callback server must implement risk controls to validate each task request. For each `CallbackRequest`, you should:

1. Analyze the request content
2. Apply your risk control policies to ensure the requested key share operation is legitimate and authorized
3. Return an approval or rejection decision

### Creating a response

To build the HTTP response, your callback server must:

1. Create a `CallbackResponse` struct based on your risk control decision
2. Serialize the `CallbackResponse` struct to JSON format to obtain `CallbackResponseJsonString`
3. Use `CallbackResponseJsonString` as the JWT payload and sign it with your callback server's RSA private key
4. Return the JWT directly in the HTTP response body to the TSS Node

<Note>
  If the TSS Node doesn't receive a response, it will retry the request. After maximum retries, the TSS Node will consider the risk control decision as "REJECT."
</Note>

## Request and response format

For detailed specifications of the callback server communication, including request types, payload formats, and response handling, see [Callback Request and Response Formats](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-data-structure).

## Next steps

* [Configure callback keys](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-configure)


# TSS Node callback mechanism
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-overview

Understanding the TSS Node callback mechanism architecture and workflow

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

The TSS Node callback mechanism is a critical component in the server co-signer solution that enables custom risk control implementation. When enabled, it reviews and approves all task requests before the TSS Node executes them.

## Sample callback server

Cobo provides example callback server implementations in multiple programming languages to help you quickly develop your callback server. You can find these examples in our [GitHub repository](https://github.com/CoboGlobal/cobo-mpc-callback-server-v2-template).

## How it works

After startup, the TSS Node establishes a persistent connection with the Cobo WaaS service to receive task requests. These tasks fall into three categories:

* **Key generation (KeyGen)**: Creating new key shares for your MPC Wallets.
* **Key signing (KeySign)**: Signing transactions or messages.
* **Key resharing (KeyReshare)**: Redistributing key shares among participants.

Without the callback mechanism, the TSS Node executes tasks directly or waits for approval from the [embedded risk control module](/developers/v2/guides/mpc-wallets/server-co-signer/embedded-risk-controls) if it is enabled. With the callback mechanism enabled, the TSS Node requests approval from your TSS Node callback servers for each task. The TSS Node only executes tasks that all of your callback servers approve.

## Callback request types

Each callback request carries a `request_type` field that identifies the operation the TSS Node asks your callback server to approve.

| `request_type` | Name             | Meaning                                                               |
| -------------- | ---------------- | --------------------------------------------------------------------- |
| `0`            | `TypePing`       | Heartbeat check that verifies your callback server is reachable.      |
| `1`            | `TypeKeyGen`     | A request to create new key shares for your MPC Wallets.              |
| `2`            | `TypeKeySign`    | A request to sign a transaction or message.                           |
| `3`            | `TypeKeyReshare` | A request to redistribute key shares to a new key share holder group. |

For the full payload schema of each request type, and for the HTTP response your callback server must return, see [Callback request and response formats](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-data-structure).

<Note>
  These callback `request_type` values are sent by the TSS Node to your callback server for approval. They are distinct from Cobo webhook event types (such as `wallets.transaction.*` and `wallets.mpc.tss_request.*`), which the WaaS service sends to notify your application of status changes. For webhook event types, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type).
</Note>

## Communication security

The TSS Node and callback server communicate via HTTP, using JSON Web Token (JWT) with RS256 signing algorithm to ensure secure data transmission. This involves:

1. **Key generation**: Both the TSS Node and callback server generate their own RSA key pairs.
2. **Key exchange**: Each component configures the other's RSA public key in their system.
3. **Request signing**: All requests are signed using the sender's private key.
4. **Signature verification**: Recipients verify signatures using the sender's public key.

To learn more about JWTs, see [Introduction to JSON Web Tokens](https://jwt.io/introduction).

## Implementation steps

To implement the callback mechanism:

1. [Deploy your TSS Node callback server](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-deploy).
2. [Configure callback keys](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-configure).
3. Start both the TSS Node and callback server.


# Backup, restore, and recovery
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/disaster-recovery-overview

Overview of backup, restore, and recovery methods for your key shares

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This guide provides an overview of different restore and recovery methods to handle system failures and disaster scenarios for your server co-signer, and a comparison between them.

## Available methods

### Backup and restore

To prevent system failures or other unforeseen scenarios, you should regularly backup your TSS Node data. This includes:

* The `secrets.db` file containing your key shares
* The encryption password for the database

Use restore when you need to:

* Move your TSS Node to a new host
* Recover from system failure using your backup

The restore process uses your backed up data to recreate your TSS Node environment exactly as it was.

For details, see [Backup key shares](/developers/v2/guides/mpc-wallets/server-co-signer/key-shares-backup) and [Restore key shares](/developers/v2/guides/mpc-wallets/server-co-signer/key-shares-restore).

### Recover

There are two recovery methods available depending on your situation:

#### Recover key shares from another active holder group

Use this method when:

* Your key share is lost and backup is not accessible
* You have another active key share holder group available

This method requires assistance from another active key share holder group to recover your key shares.

For details, see [Recover key shares from another active holder group](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/recover-from-active-keys).

#### Recover root extended private keys

In the unlikely event of Cobo Portal discontinuing its services, you can reconstruct the root extended private keys corresponding to the vault by utilizing an active Recovery Group.

For details, see [Recover root extended private keys](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/recover-root-key).

## Method comparison

| Method                                              | When to use                          | Prerequisites       | Cobo service required |
| --------------------------------------------------- | ------------------------------------ | ------------------- | --------------------- |
| Backup and restore                                  | Moving to new host or system failure | Backup data         | Not required          |
| Recover key shares from another active holder group | Lost key share without backup        | Active holder group | Required              |
| Recover root extended private keys                  | Cobo service unavailable             | A recovery group    | Not required          |

## Best practices

1. **Regular backups**
   * Back up your TSS Node data regularly
   * Store backups in secure locations

2. **Testing**
   * Regularly test your restore and recovery processes
   * Verify key functionality after any operation


# Embedded risk control mechanism
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/embedded-risk-controls

Configure basic risk controls in the server co-signer

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

The embedded risk control mechanism is a basic risk control mechanism built into the TSS Node. It evaluates task requests based on predefined rules that cannot be customized. A task request must be approved by both the embedded risk control module (if enabled) and all configured [callback servers](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-overview) before it can proceed.

## Configurations

The embedded risk control module can be configured through the `configs/cobo-tss-node-config.yaml` file. The configuration defines rules for the following task requests:

* Key generation (KeyGen): Creating new key shares for MPC Wallets
* Key signing (KeySign): Signing transactions or messages
* Key resharing (KeyReshare): Redistributing key shares among participants

Here's an example configuration:

```yaml theme={null}
embedded_risk_control_rules:
  enable: true
  key_gen:
    reject_all: false
    allow_list:
      - threshold: 2
        node_ids:
          - <Cobo TSS Node ID>
          - <ThirdParty TSS Node ID>
          - <Customer TSS Node ID>
  key_sign:
    reject_all: true
  key_reshare:
    reject_all: false
    allow_list:
      - xpubkey: <EXTENDED_ROOT_PUBKEY>
        new_threshold: 2
        new_node_ids:
          - <Cobo TSS Node ID>
          - <ThirdParty TSS Node ID>
          - <Customer TSS Node ID>
  key_share_sign:
    reject_all: true
```

* `enable`: Enable or disable the embedded risk control mechanism
* `key_gen.reject_all`: If true, reject all key generation requests
* `key_sign.reject_all`: If true, reject all key signing requests
* `key_share_sign.reject_all`: If true, reject all requests to sign messages for key share verification
* `key_reshare.reject_all`: If true, reject all key resharing requests
* `<key_gen>.allow_list` or `<key_reshare>.allow_list`: List of allowed key generation or resharing configurations
  * `xpubkey`: Root extended public key for key resharing
  * `new_threshold`: The new signature threshold
  * `new_node_ids`: Node IDs of the parties allowed in key resharing

Replace the placeholders with actual values:

* `<EXTENDED_ROOT_PUBKEY>`: The MPC Wallet's root extended public key
* `<Cobo TSS Node ID>`: Cobo's TSS Node ID
* `<Customer TSS Node ID>`: Your TSS Node ID
* `<ThirdParty TSS Node ID>`: A third-party TSS Node ID

To learn more about the TSS Node configuration, see [Configure the TSS Node](/developers/v2/guides/mpc-wallets/server-co-signer/appendix#configure-the-tss-node).

## Security recommendations

1. While the embedded risk control mechanism provides basic security, it's strongly recommended to also implement the callback mechanism for additional custom risk controls. This combination offers a more comprehensive and flexible risk management strategy.
2. Regularly review and update your risk control configurations
3. Test your configurations in a development environment before deploying to production

## Next steps

* [Deploy your callback server](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-overview)


# Verify key shares
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/key-share-verify

Learn how to verify your key shares to ensure they are valid and properly configured

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Regular verification of key shares in MPC Wallets is crucial to maintaining their integrity and security. This process helps detect issues like corruption, unauthorized modifications, or loss of key shares.

This article introduces the methods you can use to verify key shares on your server co-signer and key shares you have exported and stored as backup files.

<Note>
  To use this feature, ensure your TSS Node is running version 0.10.0 or higher.
</Note>

## How it works

The verification process involves:

1. Using the key share to sign some data
2. Verifying the signature using the original data and the key share's public key

## Verify active key shares

This section explains how to verify your active key shares - the ones currently in use in your TSS Node.

<Note>
  For TSS Nodes kept offline, an alternative verification method is required. We are currently developing this feature and will provide detailed instructions in the near future.
</Note>

1. Follow the instructions in [Verify key shares](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/key-share-verification) to trigger recurring or one-time key share verification in Cobo Portal.
2. Cobo Portal will verify the signed message and displays the result. If you want to verify by yourself, you can use either online tools or your local environment.

   <Note>Currently, key share verification through the Cobo Portal is only supported for Organization-Controlled Wallets.</Note>

   * Using online tools

     1. Go to [Google Colab](https://colab.research.google.com/)
     2. Paste the verification code below
        * You can retrieve the original and signed message by clicking <img alt="View key share verification details" /> next to the key share you want to check.<img alt="View key share verification details" />
        * You can run the [info group](/developers/v2/guides/mpc-wallets/server-co-signer/appendix#info-group) command to get the share public key.

     ```python theme={null}
     import ed25519
     from hashlib import sha256

     message = bytes.fromhex("<ORIGINAL_MESSAGE>")
     public = "<SHARE_PUBLIC_KEY>"
     signature = '<SIGNATURE>'

     VerifyKey = ed25519.VerifyingKey(bytes.fromhex(public))
     print("VerifyKey: ", VerifyKey.to_bytes().hex())

     hashmsg = sha256(message)
     print("Hash message: ", hashmsg.hexdigest())

     try:
         VerifyKey.verify(signature, hashmsg.digest(), encoding='hex')
         print("ed25519 verify pass!")
     except:
         print("ed25519 verify failed!")
     ```

     3. Run the code to verify signatures

   * Local verification
     1. Set up your environment:
     ```bash theme={null}
     pip3 install ecdsa
     pip3 install ed25519
     ```
     2. Create a `checker.py` file with the verification code above.
     3. Run the code to verify signatures

### Manual key share verification and callback risk control

Key share verification (also called manual key share verification or manual verification) is enabled by default in a TSS Node. If you want to disable key share verification by using the embedded risk control module, you can modify the `configs/cobo-tss-node-config.yaml` file as follows:

```yaml theme={null}
embedded_risk_control_rules:
  enable: true
  key_share_sign:
    reject_all: true
```

By default, the TSS Node callback does not perform risk control for key share verification, and there is no self-serve callback `check_policy` configuration to turn it on. The only built-in control is the embedded risk control module shown above, configured through `embedded_risk_control_rules.enable` together with `key_share_sign.reject_all` in `configs/cobo-tss-node-config.yaml`. To enable callback-based risk control for key share verification for your organization, contact Cobo at <a href="mailto:help@cobo.com">[help@cobo.com](mailto:help@cobo.com)</a>.

## Verify backup key shares

This feature is under development. Stay tuned for updates.


# Back up your key share
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/key-shares-backup

Learn how to back up your key share.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This article introduces how to back up your key share once you have successfully generated it.

## Prerequisites

* Before proceeding with the backup, please ensure that you have completed the TSS Node initialization by following the steps in [Deploy a TSS Node](/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-deployment).

* You must have [created a key share holder group through Cobo Portal](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/holder-group-overview).

## Verify the root extended public key

You must first check the local key share information before backup and ensure that the root extended public key displayed in Cobo Portal matches the one shown in the TSS Node log.

1. Navigate to the corresponding vault page and click on the **Key Share Management** icon.

<img alt="A Key Share Management icon" />

2. You can see the root extended public keys in the **Key Share Management** page.

<img alt="A root extended public key" />

3. Execute the following command to check the root extended public keys in the TSS Node log:

   ```
   sudo ./tss-node.sh info group
   ```

   Example:

   ```
   $ sudo ./tss-node.sh info group
   Container started: bc5e54bc4675a46b3edc9bbabc76ebb7d3918260fe8aeb09bbd60375ae26438c
   Wait a few seconds ..................
   INFO[2022-12-14T09:51:28+08:00] Total number of groups: 2, from db/secrets.db
   INFO[2023-01-16T09:04:12+08:00] Group info: 
       Group ID: OoQGkknsPdPjLCmSuuSf
       Created Time: 2023-01-09 17:42:21.391854 +0800 HKT
       Root Extended Public Key: xpub661MyMwAqRbcGNFddDqGveSvN9jr1n1GMGFypyhqn34oKyMw9bvrych636CDwgBbLjdLgQRoQtmqPucPb1pZQVBZq3tuXXTQX8wP3JMWAak
       ChainCode: 0xb74087d551e44ef8d3a1270accb1977fd373c29fe6e235bc681c59a2137e1334
       Share ID: 914259450665435839517029445012417071559
       Share Public Key: 0x023633989378b01c2e66d5fd70666101546a310aaab2c08c7b5813be371d438c0d
       Type: 1
       Curve: secp256k1
       Threshold: 2
       Local Node ID: cobo2Jitd83uNFZmGnvs8c4Bs1TUNjVVeBQmc82a4KpLFqdbLs
       Other Node IDs: [coboBP97RpWKD2WGKhUUtZ1iu6uyWL7MjY4S8MpTUHDiwvRni cobok1nJ4P8DL1mU5SDEzh8QDA5FzdSg7gdkAZKUWK4NuviS4]
       Participants: 3
         (1) Node ID: coboBP97RpWKD2WGKhUUtZ1iu6uyWL7MjY4S8MpTUHDiwvRni
             Share ID: 751341643106997665517612415491881522730
             Share Public Key: 0x02ad8728dce88aa210645cff8dea474114376796d81e4b4df76bfa3ea847131b57
         (2) Node ID: cobo2Jitd83uNFZmGnvs8c4Bs1TUNjVVeBQmc82a4KpLFqdbLs
             Share ID: 914259450665435839517029445012417071559
             Share Public Key: 0x023633989378b01c2e66d5fd70666101546a310aaab2c08c7b5813be371d438c0d
         (3) Node ID: cobok1nJ4P8DL1mU5SDEzh8QDA5FzdSg7gdkAZKUWK4NuviS4
             Share ID: 997493310528521058725882883276549657588
             Share Public Key: 0x02a233d2d37297bcfc3092ea65997a29b72931b5ca343db5cd608c85a306be5994
   ```

   Verify that the root extended public key shown in the above log matches the one displayed in Cobo Portal. Otherwise, the backup data will be invalid.

## Back up your key share

After verification, please back up the following data:

1. The encrypted database file located at `db/secrets.db`.
2. The database encryption password, which is the password you set during the TSS Node initialization process.

Both items are critical components of your key share. Losing either one will result in the complete loss of access to your private key. It is crucial to back up both items securely, but they must NOT be stored together, as this would be equivalent to keeping a key with its lock, which compromises security.


# Restore key shares
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/key-shares-restore

Guide to restoring TSS Node key shares from backup

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Restoring key shares means moving your backed up TSS Node data to a new host and configuring it to run with the same key shares as before. This process is necessary when you need to migrate your TSS Node to a different server or recover from a system failure.

You should restore your key shares on a host with the same environment as the original deployment. For example, if your `secrets.db` was generated on a Mac, you should set up a new Mac environment for restoration. Ensure the new host meets the server requirements specified in [Server requirements for deploying a TSS Node](/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-server-environments).

## Prerequisites

Before restoring your key shares:

1. Set up the TSS Node environment on your new host following the [server requirements](/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-server-environments)
2. Download the same version of TSS Node software package that was used for the backup

## Restore process

1. Extract the TSS Node software package
2. Copy your backed up `db` folder to the extracted directory
3. Start the TSS Node

## Verify restoration

1. Check your key share information:

```bash theme={null}
sudo ./tss-node.sh info group
```

2. In the output log, verify that the root extended public key matches the one displayed in Cobo Portal.

## Complete restoration

1. Restart your TSS Node
2. Enter the encryption password used when creating the backup
3. If the password is correct, your TSS Node will start running normally on the new host


# Risk control best practices for server co-signers
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/risk-control-best-practices



<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

There are two risk control mechanisms for server co-signers: Embedded risk control and TSS Node callback. This guide introduces the security best practices for implementing these two mechanisms.

* Embedded risk control provides basic, predefined rules that cannot be customized. You configure risk control rules in the `configs/cobo-tss-node-config.yaml` file.

* For TSS Node callback, you implement custom risk control logic in your callback server to check callback requests against your specific rules. Key fields to check in the callback request:
  * `request_detail`: Contains critical information about key generation, key resharing, and transaction signing.
  * `extra_info`: Provides additional context; should be cross-referenced with `request_detail` for validation.

## Key generation

We recommend using embedded risk control for key generation requests. Callback server logic is usually not needed for this operation.

Configure embedded risk control for key generation like this:

```yaml theme={null}
embedded_risk_control_rules:
  enable: true
  key_gen:
    reject_all: false
    allow_list:
      - threshold: 2
        node_ids:
          - <Cobo TSS Node ID>
          - <ThirdParty TSS Node ID>
          - <Customer TSS Node ID>
  key_sign:
    reject_all: true
  key_reshare:
    reject_all: true
  key_share_sign:
    reject_all: true
```

This configuration:

* Allows key generation with specified threshold and TSS Node IDs
* Rejects all other requests

## Key resharing

We recommend using embedded risk control for key resharing requests. Callback server logic is usually not needed for this operation.

Configure embedded risk control for key resharing like this:

```yaml theme={null}
embedded_risk_control_rules:
  enable: true
  key_gen:
    reject_all: true
  key_sign:
    reject_all: true
  key_reshare:
    reject_all: false
    allow_list:
      - xpubkey: <EXTENDED_ROOT_PUBKEY>
        new_threshold: 2
        new_node_ids:
          - <Cobo TSS Node ID>
          - <ThirdParty TSS Node ID>
          - <Customer TSS Node ID>
  key_share_sign:
    reject_all: true
```

This configuration:

* Allows key resharing requests from a specified key share holder group, threshold, and TSS Node IDs.
* Rejects all other requests

## Transaction signing

We recommend using both embedded risk control and callback server logic for transaction signing requests.

### Embedded risk control

Configure your embedded risk control rules for transaction signing:

```yaml theme={null}
embedded_risk_control_rules:
  enable: true
  key_gen:
    reject_all: true
  key_sign:
    reject_all: false
  key_reshare:
    reject_all: true
  key_share_sign:
    reject_all: true
```

This configuration allows only signing requests while rejecting all other requests.

### Callback risk control

Implement these security checks in your TSS Node callback server:

1. Verify the transaction hash to prevent transaction tampering:
   1. Extract the raw transaction data from `extra_info.Transaction.RawTxInfo.UnsignedRawTx`
   2. Calculate the hash of this raw transaction data according to the rules of the specific chain
   3. Compare the calculated hash with the value in `request_detail.msg_hash_list`
   4. Reject the transaction if the hashes don't match

2. Validate critical transaction parameters to prevent unauthorized or malicious transactions
   1. Parse `extra_info.Transaction.RawTxInfo.UnsignedRawTx` according to the chain format, and extract key transaction parameters such as:
      * Gas fee: Ensure it is within acceptable ranges
      * Destination address: Verify against allowed addresses
      * Transaction amount: Check against configured limits
      * Chain ID: Confirm it matches your expected network
      * Call data
      * Other specific parameters as needed
   2. Compare the parsed parameters with those in `extra_info.Transaction`
   3. Compare the parsed parameters or `extra_info.Transaction` with the original transaction created using the WaaS 2.0 API

Additional information to verify (not security-critical):

* Validate the signing key share:

  * `tweak_list`: The list of tweaks to apply.
  * `bip32_path_list`: BIP32 derivation paths.
  * `root_pub_key`: Root extended public key of the key share holder group.

  Use these to derive the address or public key of the signing key, ensuring correctness. An incorrect key could lead to withdrawals from unintended addresses.

* Check `signature_type` compatibility with the target blockchain, as signature types vary across chains.

## Auto-sweeping implementation

For MPC Wallets with auto-sweeping enabled, implement a whitelist-based approval system that:

1. Verifies the transaction hash to ensure transaction integrity.
2. Checks if the destination address is on the pre-approved whitelist.
3. Automatically approves transactions that meet both criteria.

The [TSS Node callback server template](https://github.com/CoboGlobal/cobo-mpc-callback-server-v2-template) provides a sample implementation of this whitelisting logic:

1. Configure the whitelist of destination addresses in [callback-server-config.yaml](https://github.com/CoboGlobal/cobo-mpc-callback-server-v2-template/blob/master/cobo-mpc-callback-server-v2-golang/configs/callback-server-config.yaml).

2. Refer to [sign.go](https://github.com/CoboGlobal/cobo-mpc-callback-server-v2-template/blob/master/cobo-mpc-callback-server-v2-golang/internal/verifier/sign.go) for examples of:
   * Parsing transaction content
   * Verifying hash against the signed message
   * Approving transactions based on the whitelist

<Note>
  Future updates will expand the sample project to support additional blockchain networks. You can also extend support to more tokens using the [token\_adapter](https://github.com/CoboGlobal/cobo-mpc-callback-server-v2-template/tree/master/cobo-mpc-callback-server-v2-golang/pkg/token_adapter) module in the repository.
</Note>


# Risk control mechanisms overview
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/risk-control-mechanisms

Understanding the risk control mechanisms in server co-signer

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

The server co-signer solution provides two risk control mechanisms to help secure your MPC Wallets:

1. Embedded risk control mechanism
2. (Recommended) TSS Node callback mechanism

The embedded risk control mechanism provides basic, non-customizable rules, while the TSS Node callback mechanism enables you to implement custom risk control logic. If both mechanisms are enabled, they work together - a task proceeds only when approved by both. We recommend implementing the callback mechanism for greater flexibility in managing your MPC Wallet security.

## Embedded risk control mechanism

The embedded risk control mechanism is a basic risk control mechanism built into the TSS Node. It:

* Can be enabled or disabled through the configuration file.
* Uses a set of predefined rules that are fixed and cannot be customized.
* Provides a foundational layer of security for your MPC Wallet operations.

For more detail about the embedded risk control mechanism, see [Embedded risk control mechanism](/developers/v2/guides/mpc-wallets/server-co-signer/embedded-risk-controls).

## TSS Node callback mechanism

The TSS Node callback mechanism provides a flexible, customizable risk control mechanism that:

* Implements your custom risk control rules.
* Reviews all task requests in real-time.
* Makes approval/rejection decisions based on your business logic.
* Communicates securely with the TSS Node using JWT authentication.

You can deploy multiple callback servers for enhanced security when you have multiple systems with different control requirements. Each callback server can have its own risk control rules, and a task request will be approved only if all configured callback servers approve.

To learn more about the TSS Node callback mechanism, see [TSS Node callback mechanism](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-overview).

## Controlled operations

Both risk control mechanisms can review and control the following task requests:

* Key generation (KeyGen): Creating new key shares for MPC Wallets.
* Key signing (KeySign): Signing transactions or messages.
* Key resharing (KeyReshare): Redistributing key shares among participants.

## Risk control workflow

The following diagram illustrates how the two risk control mechanisms work together:

<img alt="Risk control workflow" />

When the TSS Node receives a task request:

* If enabled, the embedded risk control module evaluates the request using its basic rules.
* If configured, the callback risk control module sends the request to all configured callback servers.

The request proceeds only if:

* The embedded risk control module approves (if enabled).
* AND all configured callback servers approve.

## Next steps

1. [Configure embedded risk controls](/developers/v2/guides/mpc-wallets/server-co-signer/embedded-risk-controls)
2. [Set up your TSS Node callback server](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-overview)


# Troubleshoot server co-signer setup
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/troubleshooting

Resolve common errors when setting up a server co-signer and generating key shares.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This page lists common errors that you may encounter when you deploy a server co-signer and generate key shares, together with their likely causes and remediation steps.

## Key generation (TypeKeyGen) fails because node IDs do not match

`TypeKeyGen` is the callback request type that the TSS Node sends to your callback server to create new key shares. The request payload includes a `node_ids` field that lists the TSS Node IDs of the key share holder group for the task. For details, see the `TypeKeyGen request` `request_detail` `node_ids` field in [Callback request and response formats](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-data-structure).

**Likely cause:** The TSS Node IDs configured for your node do not match the TSS Node IDs of the key share holder group for the key generation task.

**Remediation:**

1. Verify the node IDs in your TSS Node configuration.
2. Compare them against the `node_ids` listed in the `TypeKeyGen` `request_detail`.
3. Correct any mismatch so that every node ID matches the key share holder group.
4. Restart the TSS Node and retry key generation.

## Related guides

* [TSS Node callback mechanism](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-overview)
* [Callback request and response formats](/developers/v2/guides/mpc-wallets/server-co-signer/callback-server-data-structure)
* [Verify key shares](/developers/v2/guides/mpc-wallets/server-co-signer/key-share-verify)


# Deploy a server co-signer
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-deployment

Learn how to deploy a server co-signer, including installing the TSS Node package and initializing the TSS Node.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This article provides a step-by-step guide on how to deploy a server co-signer, covering the installation of the TSS Node package and the initialization and start of the TSS Node.

## Prerequisites

Before deploying a server co-signer, make sure your environment meets our network and server requirements. For detailed information about:

* Server specifications and security recommendations, see [Server environments](/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-server-environments)
* Network connectivity and environments, see [Network environments](/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-network-environments)

## Install the TSS Node package

To begin with, install the TSS Node package on your server.

### Acquire the TSS Node package

The TSS Node package comes in two versions tailored to different deployment environments:

* **SGX security enhanced version**: Designed for servers equipped with SGX capabilities. You can download this TSS Node package [here](https://cobo-tss-node.s3.amazonaws.com/linux-sgx/latest/cobo-tss-node-linux-sgx.tgz) and the corresponding SHA256 file [here](https://cobo-tss-node.s3.amazonaws.com/linux-sgx/latest/cobo-tss-node-linux-sgx.tgz.sha256).

* **General version**: Compatible with all servers, including those from cloud providers, custom-built servers, general servers, and Apple MacBooks. While this version can also run on SGX-ready servers, SGX-specific features will not be enabled. You can download this TSS Node package [here](https://cobo-tss-node.s3.amazonaws.com/generic/latest/cobo-tss-node-generic.tgz) and the corresponding SHA256 file [here](https://cobo-tss-node.s3.amazonaws.com/generic/latest/cobo-tss-node-generic.tgz.sha256).

The subsequent example employs the general version of the TSS Node package.

```
cobo-tss-node-generic.tgz (TSS Node file)

cobo-tss-node-generic.tgz.sha256 (hash file）
```

To verify the package integrity:

1. Display the expected checksum from the SHA256 file:

```bash theme={null}
cat cobo-tss-node-generic.tgz.sha256
```

2. Compare it with the actual checksum of your downloaded package. They must match exactly:

```bash theme={null}
sha256sum cobo-tss-node-generic.tgz
```

<Note>If you are using an Apple MacBook, use `shasum -a 256` instead:</Note>

```bash theme={null}
shasum -a 256 cobo-tss-node-generic.tgz
```

If the checksums don't match, the package may have been corrupted during download or tampered with. In this case, please download the package again.

After verification, please execute the following command to unzip the TSS Node package.

```
tar -xzf cobo-tss-node-generic.tgz
```

Upon extracting the TSS Node package, the following directory will be shown.

```
cobo-tss-node-generic

├── configs

│ └── cobo-tss-node-config.yaml.template （default config file template）

└── tss-node.sh （startup script）
```

Unless stated otherwise, please execute all subsequent commands in this user guide under the root directory of the unzipped TSS Node package. For example, navigate to the **cobo-tss-node-generic** path before running any further commands.

### **TSS Node command line commands**

The TSS Node command line commands remain consistent across all deployment environments. However, the execution of commands may vary slightly. For both SGX-ready servers and other types of servers, sudo access is essential for deploying and running TSS Node. In other words, ensure that sudo commands are inserted.

```
sudo ./tss-node.sh status
```

For the Apple MacBook, no sudo access is required.

```
./tss-node.sh status
```

Unless explicitly stated otherwise, all subsequent commands in this user guide will use the general server as an example.

To learn more about the TSS Node command line commands, please refer to [TSS Node command line commands](/developers/v2/guides/mpc-wallets/server-co-signer/appendix#tss-node-commands).

### **Fetch the TSS Node container image**

Please execute the following command to verify the installation of necessary dependencies and drivers. If this marks the initial configuration of the TSS Node, the command will also automatically fetch the latest container image.

```
sudo ./tss-node.sh status
```

The output example is as follows.

```
$ sudo ./tss-node.sh status

[sudo] password for ubuntu: (ubuntu account password)

Checking docker engine ... OK, version: 20.10.22

Checking container image ... Image not found: coboglobal/tss-node:v0.10.0

Going to pull container image coboglobal/tss-node:v0.10.0 …

Login Succeeded

v0.10.0: Pulling from coboglobal/tss-node

4e7e0215f4ad: Pull complete

7fd35d9d7f31: Pull complete

86c277e0f34d: Pull complete

4f4fb700ef54: Pull complete

Digest: sha256:9dd6c67522b6f36df61e2a945d6093683fd4c980e5e15d3bcdd661ca8e062578

Status: Downloaded newer image for coboglobal/tss-node:v0.10.0

docker.io/coboglobal/tss-node:v0.10.0

Checking container image ... OK, id: sha256:8ab0c7353f5b62cdff5bdc6d9a436f0d99079d404b080aa6a61f594fe6446ba8

Checking TSS-node daemon ... not running

Please use './tss-node.sh start' to start the daemon.

Please use './tss-node.sh init' if the tss-node is not initialized yet.
```

As of now, all dependencies are considered successfully configured, and the TSS Node is ready for initialization.

### Configure the TSS Node

The default config file is `configs/cobo-tss-node-config.yaml.template`.

The TSS Node is configured to connect to the development environment by default, requiring no additional config file for it to run. However, if you wish to connect to the production environment, manual modification of the config file is necessary.

To initiate this, create a duplicate of `cobo-tss-node-config.yaml.template`, renaming it as cobo-tss-node-config.yaml. Paste the new file into the `configs` directory. For instructions, please refer to [Configure the TSS Node](/developers/v2/guides/mpc-wallets/server-co-signer/appendix#configure-the-tss-node). Remember to restart the TSS Node package once the config file is modified.

### Startup script

The TSS Node package incorporates a startup script, `tss-node.sh`, that serves the following purposes:

* Checks whether the required software and drivers are successfully installed.
* Pulls the container image of the TSS Node.
* Manages the running status of the containers.

The startup script will pass in most commands and parameters to the cobo-tss-node program within the containers.

## Initialize the TSS Node

Please execute the following command:

```
sudo ./tss-node.sh init
```

The output example is as follows:

```
$ sudo ./tss-node.sh init

[sudo] password for ubuntu: (ubuntu account password)

Type password (at least 16 characters): (enter password)

Retype password: (re-enter password)

INFO[2023-01-13T05:12:04Z] Initialize database: db/secrets.db

INFO[2023-01-13T05:12:04Z] Initialize Node ID: cobo73VA6C6WvofPg8tWYmqvdUF1cPYhd7EmGUxTexz5HCzYe

INFO[2023-01-13T05:12:04Z] Generate callback public key:

-----BEGIN PUBLIC KEY-----

MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAomg0FRc8qm/vdNnjBDBv

DzKK7cZeeoRFAw2xcuaKWyCRHazERYAmICWG+q6dGZ8eS0C8AUqeqf23LlY3gDtr

...

TQIDAQAB

-----END PUBLIC KEY-----

INFO[2023-01-13T05:12:04Z] Start to initialize TSS parameters; the process may take several minutes

INFO[2023-01-13T05:12:11Z] Complete initialization of TSS parameters

INFO[2023-01-13T05:12:11Z] Complete initialization of TSS Node keys and data
```

Execution Workflow:

* During TSS Node initialization, the system will verify the successful installation of Docker Engine and proceed to build the container image. You will be prompted to approve the auto installation of Docker Engine.
* If an SGX-ready server is utilized, the system will additionally verify the successful installation of the SGX driver. You will be prompted to approve the auto installation of the Intel DCAP 1.41 driver.
* Set a password to encrypt the data generated during TSS Node initialization. In the event of lost access or the need to modify the password, please refer to [Recover key shares from another active holder group](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/recover-from-active-keys). It is recommended to set a complex password with a length between 16-32 characters, utilizing a password manager (e.g., 1Password), and securely store the password on a trusted device.
* The database file will be automatically generated with the default path being `db/secrets.db`.
* The Node ID will be automatically generated (e.g., cobo73VA6C6WvofPg8tWYmqvdUF1cPYhd7EmGUxTexz5HCzYe) and functions as the unique identifier of the TSS Node.
* The TSS Node callback private key, which is a private key for authenticating the communication with the TSS Node callback server, will be automatically generated and the corresponding public key will be printed.

## Start the TSS Node

Execute the following command to start the TSS Node:

```
sudo ./tss-node.sh start
```

The output example is as follows:

```
$ sudo ./tss-node.sh start

Container started: 4d33d31066279927bd0f9e283aa60454ac02a040a6f49e684ee372321bd41065

Wait a few seconds ..

Enter password: (type password)

cobo-tss-node

Version: v0.10.0

Build mode: prod

Git commit: 45431a4b3d4ad8ddf4a52aab619f41353310f0ba

Build time: 20230112T111204

INFO[2023-01-13T05:13:32Z] Waiting for password input on HTTP endpoint.

Embedded Risk Control Rule:

|__ Enable: false

INFO[2023-01-13T05:15:09Z] TSS Node ID: cobo73VA6C6WvofPg8tWYmqvdUF1cPYhd7EmGUxTexz5HCzYe

INFO[2023-01-13T05:15:09Z] WebSocket connecting to wss://ws.tss.dev.cobo.com/ws

INFO[2023-01-13T05:15:10Z] Start to register service
```

At this stage, the TSS Node is ready to be included in a key share holder group. Once you create a holder group with this TSS Node, you'll see a successful registration status in the logs.

## Create a key share holder group

You can now proceed with [creating a holder group through Cobo Portal](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/holder-group-overview) with this TSS Node.

Upon successful creation of the holder group, the registration status will be updated to the following:

```
INFO[2023-01-13T05:17:09Z] TSS Node registration accepted
```

You can press Ctrl+C to exit, and the TSS Node will continue to run in the background. For more information on checking the status of the TSS Node, please refer to [TSS Node commands](/developers/v2/guides/mpc-wallets/server-co-signer/appendix#tss-node-commands).

## Manage the key share

Once you have successfully created a key share holder group with this TSS Node, the generated key share will be encrypted and stored locally in the database file of the TSS Node package. The default path is `db/secrets.db`. It is highly recommended to create backups of the database file and the password used for encryption during the initialization of the TSS Node. The backup files should be stored on separate devices for enhanced security. For more information, please refer to [Back up your key share](/developers/v2/guides/mpc-wallets/server-co-signer/key-shares-backup).

## Export metrics

The TSS Node supports exporting server metrics to your InfluxDB database for performance monitoring. These metrics can be visualized using Grafana for comprehensive insights. To configure metric export, see [Configure the TSS Node](/developers/v2/guides/mpc-wallets/server-co-signer/appendix#configure-the-tss-node) section. For additional assistance, contact our support team at [help@cobo.com](mailto:help@cobo.com).


# Network environments for deploying a server co-signer
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-network-environments

Learn about the network environments required for deploying a server co-signer.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

A server co-signer requires the following network environments to run optimally:

* No inbound connections are required.
* During installation (or upgrade) phase:
  * Able to access the apt sources of the system to install all necessary dependencies (only applicable to Ubuntu servers)
  * Able to access the Docker Engine installation files to install the Docker Engine
  * Able to access docker.io registry (the public Docker registry)
  * Able to access the Intel website to download the driver (applicable to a SGX-ready server)
* Runtime network requirements: Your server must have outbound access to the following endpoints:

  | Environment | Port | Domain              |
  | ----------- | ---- | ------------------- |
  | Development | 443  | ws.tss.dev.cobo.com |
  | Production  | 443  | ws.tss.cobo.com     |

  If you have configured a TSS Node callback server, the server co-signer should also be able to access the callback server.


# Introduction to server co-signers
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-overview

Overview of server co-signers using TSS Node for automated transaction signing.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

A server co-signer is a server node that uses the threshold signature scheme (TSS) Node package to automate transaction signing without manual intervention. This allows you to automate your transaction signing process and improve the overall efficiency of your workflows.

To ensure the safety of your assets and transactions, it is highly recommended that you also set up a TSS Node callback server to add custom risk controls to your signing process.

## Technical architecture

The following diagram illustrates how the server co-signer interacts with the Cobo Wallet-as-a-Service (WaaS) service and the TSS Node callback server, as well as the key components in each of these systems:

<img alt="server co-signer's technical architecture" />

### Server co-signer (TSS Node)

The TSS Node, which serves as a server co-signer, consists of the following main components that work together to ensure security and efficiency:

#### TSS logic

Implements core TSS operations, such as generating key shares, signing transactions and messages, and resharing keys, based on the MPC-TSS protocol.

#### Secrets.db

Provides encrypted storage for your MPC Wallets' key shares and the TSS Node's callback private key. The callback private key is used to sign the node's JSON Web Tokens (JWTs) sent to the TSS Node’s callback server. The database file itself is encrypted to ensure the security of its contents.

The callback private key is generated during TSS Node initialization, and the key shares are generated after completing key generation or resharing operations.

#### Embedded risk control module

A module within the TSS Node that implements the embedded risk control mechanism, one of the [two risk control mechanisms](/developers/v2/guides/mpc-wallets/server-co-signer/risk-control-mechanisms) provided by the server co-signer solution.

When both mechanisms are enabled, a task request must be approved by both the embedded risk control module and all TSS Node callback servers to proceed. If any component (embedded or callback) rejects the operation, it will be denied.

#### Callback risk control module

A module within the TSS Node that implements the TSS Node callback mechanism, one of the [two risk control mechanisms](/developers/v2/guides/mpc-wallets/server-co-signer/risk-control-mechanisms) provided by the server co-signer solution. This module:

* Sends task request details to the TSS Node callback server for risk assessment.
* Receives and processes approval/rejection decisions made by the TSS Node callback server.

It is strongly recommended that you use the TSS Node callback mechanism to add custom risk controls, especially for key signing requests.

#### Configs

Contains configurations for the TSS Node, including:

* Embedded risk control rules that are used by the embedded risk control module to decide whether to approve or reject a TSS operation request.
* Configurations about the TSS Node callback servers, including the callback server’s URL and public key which is used to verify the callback server's JWT.
* System configurations, such as the operating environment.

To learn more about the configuration options, see [Configure the TSS Node](/developers/v2/guides/mpc-wallets/server-co-signer/appendix#configure-the-tss-node).

### Metrics

You can configure to export server metrics to your InfluxDB database in order to monitor the performance of the TSS Node.

To learn more about the configuration details of metrics, see [Configure the TSS Node](/developers/v2/guides/mpc-wallets/server-co-signer/appendix#configure-the-tss-node).

### Cobo WaaS Service

The Cobo Wallet-as-a-Service (WaaS) 2.0 service requests the server co-signer to generate key shares, sign transactions or messages, or reshare keys for your MPC Wallets.

### TSS Node callback server

The TSS Node callback server is a server that implements the TSS Node callback mechanism, one of the [two risk control mechanisms](/developers/v2/guides/mpc-wallets/server-co-signer/risk-control-mechanisms) provided by the server co-signer solution.

You can enhance security by setting up one or more TSS Node callback servers that:

* Implements custom risk control rules and provides real-time approval/rejection for transaction or message signing, key generation, or key resharing.
* Uses JWTs to authenticate requests from the TSS Node
* If any configured callback server rejects a transaction, the entire operation will be denied regardless of other approvals.

The callback server should store two keys: a private key used to sign the JWT sent to the TSS Node, and the TSS Node's callback public key used to verify the TSS Node's JWT.

Cobo provides example callback server implementations in multiple programming languages to help you quickly develop your callback server. You can find these examples in our [GitHub repository](https://github.com/CoboGlobal/cobo-mpc-callback-server-v2-template).

## Next Steps

Now that you understand the architecture, you can:

1. [Set up a server co-signer](/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-deployment)
2. [Configure your risk controls](/developers/v2/guides/mpc-wallets/server-co-signer/risk-control-mechanisms)
3. [Back up your key shares](/developers/v2/guides/mpc-wallets/server-co-signer/key-shares-backup) and learn other [disaster recovery options](/developers/v2/guides/mpc-wallets/server-co-signer/disaster-recovery-overview).


# TSS Node package release notes
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-release-notes

Release notes for the TSS Node package, detailing updates and new features.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## v0.11.1

* Upgrade dependencies to resolve security issues.
* Add TSS event publish functionality.
* Fixed issue: When the callback's `retry_time` is set to `0`, it will keep retrying.
* Report configuration information when TSS Node registers.

## v0.10.0

* You can now verify key shares in Cobo Portal. For details, see [Verify key shares](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/key-share-verification).
* The data structure of the TSS Node callback request has been updated.
* Fixed several issues.

## v0.9.5

* Added `signature_type` and `tss_protocol` in the TSS Node callback request.
* Added support for non-empty tweak values when the signature type is Schnorr.

## v0.9.4

* Added support for Schnorr signature.
* Updated the `tss-node.sh` script.
* Added password segmentation feature and modified new password length restrictions.
* Modified folder and file creation permissions.

## v0.9.0

* Added callback request timeout configuration.
* Added callback service monitoring configuration.
* Added tweaklist to callback service request parameters.
* Callback service configuration now supports policy.
* Modified recovery group file format exported via export-share.
* Added change password functionality.
* Enhanced migrate command with data migration and optimization.
* Fixed issues identified in security audit.
* Optimized and upgraded MPC security protocol.
* Added support for connecting to MySQL for private key storage.
* Improved overall system performance and reliability.

## v0.7.0

* Implemented security enhancements for specific modules.
* Enhanced the "migrate" command to include data migration and optimization.
* Adjusted the priorities of configuration files and command lines.
* Added the capability to notify clients when the callback service rejects a request.
* Improved overall system performance and reliability.
* Addressed bug fixes.

## v0.6.0

* Revamped the underlying MPC protocol implementation to reinforce security.
* Established default connectivity to the development environment.
* Upgraded system message formats and encryption methods.
* Refactored the TSS Node registration mechanism.
* Introduced Canonical Group ID and Protocol Group ID.
* Enabled automated handling of sessions with abnormal statuses.
* Expanded recovery file data fields.
* Refactored the TSS Node callback mechanism.
* Optimized database structure and log system.
* Enhanced overall system performance and reliability.


# Server requirements for deploying a server co-signer
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-server-environments

Minimum and recommended server requirements for hosting a TSS Node.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This article outlines the minimum and recommended requirements for servers that host a TSS Node.

TSS Node currently supports three deployment environments:

1. [SGX-enabled servers](#intel%C2%AE-sgx)
2. [General servers](#general-server)
3. [Apple MacBook](#apple-macbook)

You can choose the deployment environment based on your business requirements.

## Intel® SGX

### Introduction to Intel® SGX

Intel® Software Guard Extensions (SGX) offers hardware-based memory encryption that isolates specific application code and data in memory. SGX allows client-level code to allocate private regions of memory, called enclaves, which are designed to be protected from processes running at higher privilege levels. It offers a granular level of control and protection against many known and active threats. For more information on Intel® SGX, please [click here](https://www.intel.com/content/www/us/en/developer/tools/software-guard-extensions/overview.html).

### SGX-ready server types

#### Azure confidential VMs

The required settings to configure a SGX-ready server are as follows:

* Select resource group: Ubuntu 20.04 LTS
* Enter a virtual machine name (e.g. CoboTSSNode)
* Select the Azure region
* Choose image: Ubuntu 20.04 LTS - Gen2
* Select virtual machine size (recommended): Standard DC1ds v3 (1 vcpu, 8 GiB memory)

For more information on how to deploy a SGX-ready server using the Azure portal, please [click here](https://learn.microsoft.com/en-us/azure/confidential-computing/quick-create-portal).

#### Alibaba Cloud Elastic Compute Service

The following settings are required to build an encrypted computing environment on a g7t, c7t, or r7t instance (vSGX instance):

* Version: Ubuntu 20.04 64-bit that works with UEFI
* Recommended memory: 8 GB and above
* Memory (encrypted data): 4 GB and above
* Hard disk: 64 GB SSD

For more information on how to deploy a SGX-ready server using the Alibaba Cloud Elastic Compute Service, please [click here](https://www.alibabacloud.com/help/en/ecs/user-guide/build-an-sgx-encrypted-computing-environment).

#### SGX-Ready physical server (on premise)

Please check the processors that support SGX:

* Head to [https://ark.intel.com/content/www/us/en/ark.html](https://ark.intel.com/content/www/us/en/ark.html)
* Click **Find products by feature** at the bottom
* Switch to the Processors tab and select **Intel® Software Guard Extensions (Intel® SGX)** in the drop-down menu.
* Select **Yes with both Intel® SPS and Intel® ME**
* Review the product specifications and configure the following settings:
  * BIOS Settings:
  * Enable Intel SGX (Software Guard Extension)
  * Enable DCAP (FLC)
  * Disable hyperthreading
  * Operating system: Ubuntu Server 20.04 LTS or 22.04 LTS
  * Recommended memory: 8 GB RAM
  * Recommended storage: 128 GB SSD
  * Minimum memory (encrypted data): 2 GB EPC

### SGX status check

Once the encrypted SGX environment has been set up, you can check the SGX status via CPUID. Please execute the following shell commands.

```
sudo apt update
sudo apt install cpuid
cpuid -1 | grep SGX
```

If the output shows three true statuses as displayed below, SGX is successfully enabled. All other false statuses are negligible.

```
SGX: Software Guard Extensions supported = true
SGX_LC: SGX launch config supported = true
SGX capability (0x12/0):
SGX1 supported = true
```

### **SGX driver installation**

The SGX driver should have already been installed by default. During TSS Node initialization, you will be prompted to approve the auto installation of the SGX driver (Intel DCAP 1.41). To verify the installation, execute the following command.

```
ls /dev/sgx*
```

If two or more nodes are displayed, it confirms that the SGX driver has been successfully installed.

```
/dev/sgx_enclave /dev/sgx_provision
```

For more information on the manual installation of a SGX driver, please refer to the following.

By default, the SGX driver is integrated into the Linux kernel starting from version 5.11 and above. It is recommended to use Linux 5.11 or above.

* Ubuntu 22.04 LTS server + default kernel
* Ubuntu 20.04 LTS server + HWE [rolling update model](https://wiki.ubuntu.com/Kernel/LTSEnablementStack)

Alternatively, you can install the DCAP driver and OOT (legacy) provided by Intel. Please note that TSS Node exclusively supports the DCAP driver. You can follow the steps below to manually install the Ubuntu 20.04 DCAP 1.41 driver. For other versions, please refer to the guide above.

1. Update the package resource list for APT.

```
sudo apt update
```

2. Install dependencies.

```
sudo apt install build-essential ocaml automake autoconf libtool \
wget python libssl-dev dkms -y
```

3. Download the Intel SGX DCAP drive.

```
wget https://download.01.org/intel-sgx/latest/linux-latest/distro/ubuntu22.04-server/sgx_linux_x64_driver_1.41.bin
```

4. Modify permissions to the driver installation packages of Intel SGX DCAP.

```
chmod a+x sgx_linux_x64_driver_1.41.bin
```

5. Install Intel SGX DCAP drive.

```
sudo ./sgx_linux_x64_driver_1.41.bin
```

6. Check whether the installation is successful.

```
$ ls /dev/sgx*
/dev/sgx_enclave /dev/sgx_provision
```

### **Docker Engine installation**

Docker Engine is required for running the TSS Node. During TSS Node initialization, you will be asked to approve the auto installation of Docker Engine. It is recommended to manually install and configure Docker Engine if your organization follows specific best practices. For more information on how to manually install the Docker Engine on Ubuntu, please [click here](https://docs.docker.com/engine/install/ubuntu/).

## General server

### **Introduction to general servers**

A general server is any server that satisfies the minimum configuration requirements for the TSS Node, such as Elastic Compute or a physical server managed by you. While a general server can host the TSS Node, it lacks the distinctive security features inherent in an SGX-ready server.

### **Minimum requirements**

* CPU: AMD64 or ARM64, 2 cores, a clock speed of 2.5 GHz
* Memory: 4 GB
* Hard disk: 64 GB SSD
* Operating system: Ubuntu Server 20.04 LTS or above

### **Recommended settings**

* CPU: AMD64 or ARM64, 4 cores, a clock speed of 3.0 GHz
* Memory: 8 GB
* Hard disk: 128 GB SSD
* Operating system: Ubuntu Server 20.04 LTS or above

### **Docker Engine installation**

Docker Engine is required for running the TSS Node. During TSS Node initialization, you will be asked to approve the auto installation of Docker Engine. It is recommended to manually install and configure Docker Engine if your organization follows specific best practices. For more information on how to manually install the Docker Engine on Ubuntu, please [click here](https://docs.docker.com/engine/install/ubuntu/).

## Apple MacBook

Please prepare a new Apple MacBook, upgrade the operating system to the [latest macOS version](https://support.apple.com/en-sg/109033) and perform the necessary security configurations.

### **Things to note**

* Avoid using unknown portable storage devices.
* Prevent your computer from syncing with iCloud.
* Refrain from logging into your Apple ID on this computer.

### **Security configurations**

* Disable Bluetooth.
* Turn off AirDrop.
* Activate FileVault for disk encryption.
* Enable the Firewall.
* Establish a complex administrator password using a password manager (e.g., 1Password).
* Set up a Lock Screen.
* Disable Handoff.

### **Advanced configurations**

If utilizing a third-party management system (e.g., Jamf), consider configuring advanced security settings:

* Ensure your computer password is a minimum of 12 characters, including at least one letter, one number, and one special character.
* Prohibit using the same password consecutively three times.
* Set a password expiration period of 90 days, and change the password when prompted.
* Disable iCloud, Apple ID, and Family Sharing.
* Turn off the App Store.
* Disable internet accounts and logins via local mail clients.
* Configure privacy settings to prevent automatic data transfer to Apple.
* Deactivate all sharing services (e.g., tethering, Bluetooth sharing, file sharing, screen sharing).
* Turn off all remote software.

### **Docker Engine installation**

Ensure Docker Engine is installed for running the TSS Node. Follow the official Docker website [instructions](https://docs.docker.com/desktop/install/mac-install/) to complete the installation of Docker Desktop for Apple MacBook.


# Update a server co-signer
Source: https://cobo.com/developers/v2/guides/mpc-wallets/server-co-signer/tss-node-update

Instructions for updating a server co-signer to the latest TSS Node version.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

When new versions of the TSS Node package are released, it is highly recommended to stay updated by upgrading to the latest version. After downloading a new version of the TSS Node package, please ensure to complete the following steps.

1. Stop the currently running TSS Node.

```
sudo ./tss-node.sh stop
```

2. Back up key data (e.g. the `secrets.db` file, the passwords or the `password.key` file, and the config file).

3. Unzip the new version of the TSS Node package and overwrite the files in the old version. You can unzip the new version in the same folder used by the previous TSS Node package.

```
tar -xzf cobo-tss-node-generic.tgz
```

4. To ensure the proper functioning of the TSS Node, check its operating environment and pull the necessary container image.

```
sudo ./tss-node.sh status
```

5. Start the new version of the TSS Node, and verify its successful startup by ensuring that the version number and key data (such as the TSS Node ID) in the log match the expected values.

```
sudo ./tss-node.sh start
```


# Changelog
Source: https://cobo.com/developers/v2/guides/overview/changelog

Detailed changelog of all additions and changes to the WaaS 2.0 API.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This changelog details all additions and changes to the WaaS 2.0 API. You can download the WaaS 2.0 API specification from [GitHub](https://github.com/CoboGlobal/developer-site/blob/master/v2/cobo_waas2_openapi_spec/dev_openapi.yaml).

For changes specific to payment-related operations, please refer to the [Release history](/developers/v2/payments/changelog) of the payment solution.

## v1.41.0

This version was released on August 5, 2026.

This release contains no API or SDK changes.

## v1.40.0

This version was released on July 22, 2026.

This release contains no API or SDK changes.

## v1.39.0

This version was released on July 9, 2026.

### New features

* Added the `token_addresses` query parameter to [List enabled tokens](/developers/v2/api-references/wallets/list-enabled-tokens) for filtering by token contract address (supports up to 500 comma-separated addresses, case-insensitive). Because the same contract address may exist on multiple chains, combine with `chain_ids` to narrow results. Native tokens have no contract address and are excluded.
* Added the `action` query parameter to [List transaction templates](/developers/v2/api-references/transactions/list-transaction-templates) for specifying the approval action type (`Transfer`, `Drop`, or `SpeedUp`). Defaults to `Transfer` when omitted.
* Enhanced [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) and [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) to include `FeePayer` in `transaction.extra` when `extra_type=FeePayer`, providing the designated Solana fee payer address.
* Added the `action` field to `user_details` in approval responses. Affected operations:
  * [Get transaction approval details](/developers/v2/api-references/transactions/get-transaction-approval-details)
  * [List transaction approval details](/developers/v2/api-references/transactions/list-transaction-approval-details)

### Compatibility changes

* Deprecated `Raw_Message_Signature` in the [Sign message](/developers/v2/api-references/transactions/sign-message) operation due to security concerns. It is no longer allowed and must not be used. It may be removed in a future version.
* Clarified wallet name constraints in the [Create wallet](/developers/v2/api-references/wallets/create-wallet) operation: the `name` field is required and cannot be empty; special characters such as `@` are not accepted and will return `400 Bad Request`.
* Clarified that fee estimates from [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) are point-in-time and short-lived. Re-estimate immediately before submitting a withdrawal to avoid rejection due to insufficient fees.
* Clarified async behavior of [Create auto sweep task](/developers/v2/api-references/autosweep/create-auto-sweep-task): returned tasks have `status` set to `Submitted` with an empty `transaction_ids` array; poll [Get auto sweep task details](/developers/v2/api-references/autosweep/get-auto-sweep-task-details) until `status` becomes `TransactionCreated`. Sweeps require native chain coin for gas from the deposit address, Fee Station, or Auto-Fuel.
* Clarified that `transaction_hash` in [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) and [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) responses may be `null` or absent before on-chain broadcast.
* Clarified Solana transaction fee fields: `fee_used` covers on-chain network fees only and excludes ATA activation rent. `rent_amount` in fee estimate responses is reserved for future ATA activation rent and is currently not populated.

## v1.38.0

This version was released on June 25, 2026.

### Compatibility changes

* Added the `result_token` field to `user_details` in the response of the [Get transaction approval details](/developers/v2/api-references/transactions/get-transaction-approval-details) operation. When verifying approval signatures, the full signing content is constructed as `{message}||{result_token}`.
* Clarified that the `PendingAuthorization` transaction status covers both manual approval steps and internal automated risk-control, KYT, and compliance screening checks. A transaction in this status does not necessarily require human action. See [Transaction statuses and sub-statuses](/developers/v2/guides/transactions/status).

## v1.37.0

This version was released on June 10, 2026.

### Compatibility changes

* Added the following new webhook event types:
  * `wallets.updated`
  * `mpc_vaults.updated`
  * `mpc_vaults.deleted`
  * `organizations.updated`
* Added two new webhook event data types, `Organization` and `FiatTransaction`, to the webhook event payload. Affected operations:
  * [Retrieve event information](/developers/v2/api-references/developers--webhooks/retrieve-event-information)
  * [List all webhook events](/developers/v2/api-references/developers--webhooks/list-all-webhook-events)

## v1.36.0

This version was released on May 27, 2026.

### New features

* Added the following Travel Rule operations:
  * [Get self-custody signature challenge](/developers/v2/api-references/travelrule/get-self-custody-signature-challenge)
  * [Create Satoshi Test challenge](/developers/v2/api-references/travelrule/create-satoshi-test-challenge)
  * [Get Satoshi Test challenge](/developers/v2/api-references/travelrule/get-satoshi-test-challenge)
  * [Cancel Satoshi Test challenge](/developers/v2/api-references/travelrule/cancel-satoshi-test-challenge)
  * [List address verifications](/developers/v2/api-references/travelrule/list-address-verifications)

### Compatibility changes

* Added the `expired_time` field to `user_details` in the response of the [Get transaction approval details](/developers/v2/api-references/transactions/get-transaction-approval-details) operation.

## v1.35.0

This version was released on May 13, 2026.

### New features

* Added `TrxRecharge` as a supported enum value for `cobo_category` in the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operation.
* Added the `caip2_chain_id` field to the `chain` object in the following operations:
  * [List supported chains](/developers/v2/api-references/wallets/list-supported-chains)
  * [List enabled chains](/developers/v2/api-references/wallets/list-enabled-chains)
  * [Get chain information](/developers/v2/api-references/wallets/get-chain-information)

## v1.34.0

This version was released on April 8, 2026.

### New features

* Added the [Cancel auto sweep task by ID](/developers/v2/api-references/autosweep/cancel-auto-sweep-task-by-id) operation for canceling an auto sweep task by task ID.
* Added the [List Fee Station fiat transactions](/developers/v2/api-references/feestation/list-fee-station-fiat-transactions) operation for listing Fee Station fiat transaction records.
* Added the `min_balance_threshold` parameter to the [Create auto sweep task](/developers/v2/api-references/autosweep/create-auto-sweep-task) operation.

## v1.33.0

This version was released on March 25, 2026.

### Compatibility changes

* Added `WalletConnectInfo` to `transaction.extra` in the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operation.

## v1.32.0

This version was released on March 11, 2026.

### Compatibility changes

* Added `object_id` and `version` fields to the responses of the following UTXO-related operations:
  * [List UTXOs](/developers/v2/api-references/wallets/list-utxos)
  * [Batch check UTXOs](/developers/v2/api-references/wallets/batch-check-utxos)

* Updated the response schema of the following transaction-related operations:

  * [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information)
  * [List all transactions](/developers/v2/api-references/transactions/list-all-transactions)

  Updates include:

  * Added `object_id` and `version` fields to `destination.tx_info`
  * Added `object_id` and `version` fields to `raw_tx_info.selected_utxos`
  * Added a new `utxo_changes` array field to `raw_tx_info`

### New features

* Added a new operation: [List transaction UTXOs](/developers/v2/api-references/wallets/list-transaction-utxos), which allows you to query output UTXO information for a transaction.

## v1.31.0

This version was released on February 4, 2026.

### Compatibility changes

* Enhanced the EOA wallet balance model to include a new `frozen` field, representing the frozen amount,Affected operations:
  * [List token balances by address](/developers/v2/api-references/wallets/list-token-balances-by-address)
  * [List address balances by token](/developers/v2/api-references/wallets/list-address-balances-by-token)
  * [Retrieve event information](/developers/v2/api-references/developers--webhooks/retrieve-event-information)
  * [List all webhook events](/developers/v2/api-references/developers--webhooks/list-all-webhook-events)
  * [List asset balances](/developers/v2/api-references/wallets--exchange-wallet/list-asset-balances)
  * [List token balances by wallet](/developers/v2/api-references/wallets/list-token-balances-by-wallet)
  * [List Fee Station token balances](/developers/v2/api-references/feestation/list-fee-station-token-balances)

### New features

* Enhanced the [Transfer token](/developers/v2/api-references/transactions/transfer-token) and [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract) operations to support a new `pre_check` request parameter, allowing you to control the transaction precheck/validation logic.
  * Currently supported for **TRON** only.

## v1.30.0

This version was released on January 22, 2026.

### Compatibility changes

* Enhanced the [List supported chains](/developers/v2/api-references/wallets/list-supported-chains), [Get chain information](/developers/v2/api-references/wallets/get-chain-information), [List enabled chains](/developers/v2/api-references/wallets/list-enabled-chains), and [List supported tokens](/developers/v2/api-references/wallets/list-supported-tokens) operations to allow requesting more items per call.
  * Increased `limit` to **500**.
  * Increased the maximum number of items in `chain_ids` and `token_ids` to **500** per request.

### New features

* Enhanced the [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) and [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operations to better identify WalletConnect-initiated transactions.
  * Added `WalletConnect` as a new value for the `cobo_category` field.
  * Added a new JSON payload to the `extra` field when `extra_type=TransactionWalletConnectInfo` to provide additional WalletConnect transaction details.

### Improvements

* Added the `request_id` query parameter to the [List swap activities](/developers/v2/api-references/swaps/list-swap-activities) operation, allowing you to filter swap activities by a specific request ID.

## v1.29.0

This version was released on December 30, 2025.

### New Features

* Added operations to submit and query KYA address screening requests:
  * [Create KYA screening requests](/developers/v2/api-references/compliance/create-kya-address-screening-requests)
  * [Get KYA address screening result](/developers/v2/api-references/compliance/get-kya-address-screening-result)
  * [List KYA address screening results](/developers/v2/api-references/compliance/list-kya-address-screening-results)

## v1.28.0

This version was released on December 17, 2025.

### Compatibility Changes

* Added the `int64` format to the `used_nonce` field in the `TransactionRawTxInfo` schema.

### New Features

* Added a new staking operation to support expanding Babylon BTC staking to the next phase:
  * [Expand Babylon BTC staking](/developers/v2/api-references/stakings/expand-babylon-btc-staking)

### Improvements

* Added support for Cosmos contracts in the [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract) operation.

## v1.27.0

This version was released on November 26, 2025.

### Improvements

* Added support for TRON smart contracts. Now you can use the [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract), [List all transactions](/developers/v2/api-references/transactions/list-all-transactions), and [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) operations to call and retrieve transactions involving TRON smart contracts.

## v1.26.0

This version was released on November 12, 2025.

### New Features

* Added new operations for managing permissions for a tokenization contract:
  * [List token permissions](/developers/v2/api-references/tokenization/list-token-permissions)
  * [Update token permissions](/developers/v2/api-references/tokenization/update-token-permissions)

* Added support for [issuing](/developers/v2/api-references/tokenization/issue-token) wrapped tokens using the CoboERC20Wrapper and SOLWrapper standards.

### Improvements

* Added the `archived` and `token_standard` properties to the `TokenizationTokenInfo` schema.

* Added the `token_standard` query parameter to the [List supported chains for tokenization](/developers/v2/api-references/tokenization/list-supported-chains-for-tokenization) operation to allow filtering by token standard.

* Deprecated the Resend transaction operation. To retry a failed transaction, please initiate a new transaction instead.

* Deprecated the Estimate transaction fee operation for Fee Station. Please use the [Check Fee Station Usage](/developers/v2/api-references/feestation/check-fee-station-usage) operation instead.

* Enhanced [Check Fee Station Usage](/developers/v2/api-references/feestation/check-fee-station-usage) operation
  * The `amount` and `token_id` request parameters are no longer required.
  * Added a new `fee_token_id` request parameter to specify the gas fee token.
  * Added a `sponsored_token_id` response field to indicate the token used to sponsor the transaction.

* Added a new `DisableAutoFuel` option for the `auto_fuel` configuration in the [Transfer token](/developers/v2/api-references/transactions/transfer-token) and [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract) operations.

* Extended `cobo_category` enums with new enums for Fee Station, tokenization, and signature-related scenarios:
  * `GasFeeSponsor`
  * `GasFeeSponsorRefund`
  * `Tokenization`
  * `TokenizationGasSponsor`
  * `TokenSwap`
  * `NonceAccountSign`
  * `FeePayerSign`

## v1.25.0

This version was released on October 29, 2025.

### New Features

* Added new operations for compliance management:
  * [Submit KYT screening decision](/developers/v2/api-references/compliance/submit-kyt-screening-decision)
  * [Submit KYT manual review result](/developers/v2/api-references/compliance/submit-kyt-manual-review-result)
  * [Get KYT screening status](/developers/v2/api-references/compliance/get-kyt-screening-status)

### Improvements

* Introduced a new [webhook event type](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types) for KYT screening status changes: `compliance.kyt.screenings.status.updated`.

## v1.24.0

This version was released on October 15, 2025.

### New Features

* You can now check whether Fee Station is applicable for a transaction by using the [Check Fee Station usage](/developers/v2/api-references/feestation/check-fee-station-usage) operation.

### Improvements

* Removed the `BTC_EIP_191_Signature` and `Raw_Message_Signature` schemas from the [Sign Message](/developers/v2/api-references/transactions/sign-message) operation.

* Added the `STELLAR_Contract` schema in the [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract) operation to support trustline management on the Stellar network.

* Added a new schema `SolContractCallAddressLookupTableAccount` to support using Solana Address Lookup Tables.

* Added the `main_transaction_id` property to indicate the main transaction in the `FuelingInfo` schema.

## v1.23.0

This version was released on September 17, 2025.

### Breaking Changes

* Updated the response schema of [List approval details](/developers/v2/api-references/transactions/list-approval-details). Several properties were added or modified.
* Updated the behavior of the [List Address Book Entries](/developers/v2/api-references/addressbooks/list-address-book-entries) operation:
  * When both `address` and `label` are provided, results are now returned only if both match (previously matched if either condition was true).
  * The `chain_id` parameter has been changed from required to optional.

### New Features

* You can now manage transaction dispositions for compliance purposes with the WaaS 2.0 API. Available operations are as follows:
  * [Isolate funds](/developers/v2/api-references/compliance/isolate-funds)
  * [Refund funds](/developers/v2/api-references/compliance/isolate-funds)
  * [Unfreeze funds](/developers/v2/api-references/compliance/unfreeze-frozen-funds)
  * [Get disposition status](/developers/v2/api-references/compliance/get-disposition-status)

* You can now get, create, update, and delete Address Book entries with the following operations:
  * [Get Address Book entry](/developers/v2/api-references/addressbooks/get-address-book-entry)
  * [Create Address Book entries](/developers/v2/api-references/addressbooks/create-address-book-entries)
  * [Update Address Book entry](/developers/v2/api-references/addressbooks/update-address-book-entry)
  * [Delete Address Book entry](/developers/v2/api-references/addressbooks/delete-address-book-entry)
    <Note>The Create Address Book entries, Update Address Book entry, and Delete Address Book entry operations are available upon request. Please contact our [customer support](mailto:help@cobo.com) to enable them.</Note>

### Improvements

* Added a property `chain_identifier` to the `chain` schema which groups chains by their execution logic. For example, `ETH` for all EVM-compatible chains (Ethereum, BNB Smart Chain, Polygon).
* Added a property `biz_org_id` to the response schema of [Get organization information](/developers/v2/api-references/organizations/get-organization-information) which can be provided to Cobo's customer support to help quickly locate the organization.
* Introduced a new [webhook event type](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types) for compliance disposition status changes: `compliance.disposition.status.updated`.

## v1.22.0

This version was released on August 27, 2025.

### New Features

* You can now issue and manage your custom tokens with the WaaS 2.0 API. Available operations are as follows:
  * Issue tokens
    * [List supported chains for tokenization](/developers/v2/api-references/tokenization/list-supported-chains-for-tokenization)
    * [Issue token](/developers/v2/api-references/tokenization/issue-token)
    * [List issued tokens](/developers/v2/api-references/tokenization/list-issued-tokens)
    * [Get token details](/developers/v2/api-references/tokenization/get-token-details)
    * [Get token holdings information](/developers/v2/api-references/tokenization/get-token-holdings-information)
  * Perform core lifecycle operations
    * [Mint tokens](/developers/v2/api-references/tokenization/mint-tokens)
    * [Burn tokens](/developers/v2/api-references/tokenization/burn-tokens)
    * [Call token contract](/developers/v2/api-references/tokenization/call-token-contract)
    * [Pause token contract](/developers/v2/api-references/tokenization/pause-token-contract)
    * [Unpause token contract](/developers/v2/api-references/tokenization/unpause-token-contract)
    * [Estimate tokenization operation fee](/developers/v2/api-references/tokenization/estimate-tokenization-operation-fee)
  * Manage token access controls
    * [Activate or deactivate allowlist](/developers/v2/api-references/tokenization/activate-or-deactivate-allowlist)
    * [Get allowlist activation status](/developers/v2/api-references/tokenization/get-allowlist-activation-status)
    * [List addresses on allowlist](/developers/v2/api-references/tokenization/list-addresses-on-allowlist)
    * [Update addresses on allowlist](/developers/v2/api-references/tokenization/update-addresses-on-allowlist)
    * [List addresses on blocklist](/developers/v2/api-references/tokenization/list-addresses-on-blocklist)
    * [Update addresses on blocklist](/developers/v2/api-references/tokenization/update-addresses-on-blocklist)
  * Monitor activities
    * [List tokenization activities](/developers/v2/api-references/tokenization/list-tokenization-activities)
    * [Get tokenization activity details](/developers/v2/api-references/tokenization/get-tokenization-activity-details)

* Added the following operations for creating and managing auto-sweep tasks and configuring sweep-to addresses:
  * [Create auto-sweep task](/developers/v2/api-references/autosweep/create-auto-sweep-task)
  * [List auto-sweep tasks](/developers/v2/api-references/autosweep/list-auto-sweep-tasks)
  * [Get auto-sweep task details](/developers/v2/api-references/autosweep/get-auto-sweep-task-details)
  * [Create sweep-to address](/developers/v2/api-references/autosweep/create-sweep-to-address)
  * [List sweep-to addresses](/developers/v2/api-references/autosweep/list-sweep-to-addresses)

* Added the following operations for tracking transaction approvals and retrieving approval templates:
  * [List approval details](/developers/v2/api-references/transactions/list-approval-details)
  * [List transaction templates](/developers/v2/api-references/transactions/list-transaction-templates)

### Improvements

* You can enable auto token sweeping for MPC Wallets and Web3 Wallets by setting the `enable_auto_sweep` parameter to `true` when using the [Creating wallet](/developers/v2/api-references/wallets/create-wallet) operation.

## v1.21.0

This version was released on August 13, 2025.

### New Features

* Added the [Estimate maximum transferable value](/developers/v2/api-references/wallets/estimate-maximum-transferable-value) operation to estimate the maximum transferable value based on specified fee settings. We recommend using this new operation instead of [Get maximum transferable value](/developers/v2/api-references/wallets/get-maximum-transferable-value), which will be deprecated in the future.

### Improvements

* Added compliance-related enums to the `TransactionCoboCategory` schema:
  * `ScreenAppRefund`
  * `ScreenAppIsolate`
  * `ComplianceRefund`
  * `ComplianceIsolate`

## v1.20.0

This version was released on July 30, 2025.

### Improvements

* Added `UsePortalPreference` as a new option to the `AutoFuelType` enum for [Fee Station](https://manuals.cobo.com/en/portal/fee-station/introduction) transactions. This option allows you to use payment preferences set on Cobo Portal instead of specifying the mode of transaction fee payment in each API call.
* The `destination` property in the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee#contractcall) request for contract calls is now optional.
* Added a maximum length limit of 65,000 characters for the `calldata` field in the [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract#body-destination-calldata) operation (EVM contract calls).

## v1.19.1

This version was released on July 17, 2025.

### Improvements

* Added support for the Solana and Filecoin fee models when creating transactions and retrieving transaction information. For more details, refer to the [Fee models](/developers/v2/guides/transactions/estimate-fees#fee-models) guide.

* Introduced new [webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types) for token or chain status changes
  * `wallet.token.disabled`
  * `wallet.chain.disabled`
  * `token.suspended.deposit`
  * `token.suspended.withdraw`

* Added a new [transaction sub-status](/developers/v2/guides/transactions/status#status-reference-table), `RejectedByCobo`, to indicate transactions rejected due to unmet compliance requirements.

## v1.18.0

This version was released on July 2, 2025.

### New Features

* Added the following operations for payer and top-up address management:
  * [Get top-up address](/developers/v2/api-references/payment/get-top-up-address)
  * [List payers](/developers/v2/api-references/payment/list-payers)
* Added the [Get organization information](/developers/v2/api-references/organizations/get-organization-information) operation to retrieve detailed information about the organization associated with the current API key.

### Improvements

* Enhanced the [List enabled tokens](/developers/v2/api-references/wallets/list-enabled-tokens) operation to support filtering by specific token IDs.
* Introduced new [webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types) for more granular and real-time balance update notifications:
  * `wallets.mpc.balance.updated`
  * `wallets.web3.balance.updated`

## v1.17.0

This version was released on June 18, 2025.

### New Features

* Enhanced [Create settlement request](/developers/v2/api-references/payment/create-settlement-request) to support crypto withdrawals, enabling direct settlement to crypto addresses. Also, added [List crypto addresses](/developers/v2/api-references/payment/list-crypto-addresses) operation to view all registered withdrawal addresses
* Added developer fee support to [Create refund order](/developers/v2/api-references/payment/create-refund-order).
* Added new OAuth operations to enable secure authentication for the Checkout SDK:
  * [Get Access Token](/developers/v2/api-references/oauth/get-access-token): Obtain the initial Access Token and Refresh Token
  * [Refresh Access Token](/developers/v2/api-references/oauth/refresh-access-token): Renew the Access Token

### Improvements

The [Transfer token](/developers/v2/api-references/transactions/transfer-token) operation now supports Custodial Wallet (Asset Wallet) transfers using a wallet ID. This feature requires whitelist access. You can contact [help@cobo.com](mailto:help@cobo.com) to request enrollment. Please note that implementing this feature may require updates to your existing transaction history data handling.

## v1.16.0

This version was released on May 28, 2025.

### New Features

* Added the following new operations for managing app workflows:
  * [List app workflows](/developers/v2/api-references/appworkflows/list-app-workflows)
  * [Request workflow approval](/developers/v2/api-references/appworkflows/request-workflow-approval)
  * [Get approval request details](/developers/v2/api-references/appworkflows/get-approval-request-details)
  * [Revoke approval request](/developers/v2/api-references/appworkflows/revoke-approval-request)
  * [List approval requests](/developers/v2/api-references/appworkflows/list-approval-requests)
* Added a new operation [Batch check UTXOs](/developers/v2/api-references/wallets/batch-check-utxos) which allows you to verify the existence and details of specified unspent transaction outputs (UTXOs) for a given wallet and token. This operation is supported for both MPC Wallets and Custodial Wallets (Web3 Wallets).

### Improvements

* Enhanced the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) operation by adding a property `replaced_transaction_id` to the request body, allowing fee estimation for replacement transactions.
* Added new values to the `TransactionCoboCategory` schema to support more use cases.
* Added a property `coinbase_maturity` to the `ChainInfo` schema to indicate the required confirmations for coinbase maturity.
* Added two [transaction sub-statuses](/developers/v2/guides/transactions/status#status-reference-table) `PendingCoboKYTCheck` and `RejectedByCoboKYT`.
* Added the `is_frozen` property to the response of the [List UTXOs](/developers/v2/api-references/wallets/list-utxos) operation. This property indicates whether each UTXO is currently frozen and unavailable for spending.

## v1.15.0

This version was released on May 14, 2025.

### Improvements

* Added the following new [transaction sub-statuses](/developers/v2/guides/transactions/status#status-reference-table) to support more granular tracking in transaction screening scenarios:
  * `PendingCoboCheck`
  * `RejectedTransactionPolicy`
  * `RejectedByScreeningApp`
  * `PendingScreeningAppCheck`
* Added the `estimated_fee_used` property to the schemas `TransactionEvmEip1559Fee`, `TransactionEvmLegacyFee`, `TransactionUtxoFee`, and `TransactionFixedFee` for MPC Wallets and Custodial Wallets (Web3 Wallets) transactions, to indicate the estimated transaction fee when retrieving transaction information.
* Added the query parameters `wallet_type` and `wallet_subtype` to the [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation, allowing you to filter transactions by wallet classification.
* Added the properties `wallet_subtype` and `encoding` to the response of the [List address book entries](/developers/v2/api-references/addressbooks/list-address-book-entries) operation, providing more context for address usage.
* Added data structures for TSS request events and callback payloads.

## v1.14.0

This version was released on April 23, 2025.

### New Features

* Added a batch of operations for payment scenarios, including pay-in orders, refund, settlements, merchants, bank accounts, and exchange rates, to support comprehensive payment workflows.
* Added the [Estimate fee for Fee Station transaction](/developers/v2/api-references/feestation/estimate-fee-for-fee-station-transaction) operation to estimate the gas fee for top-up transactions sent by [Fee Station](https://manuals.cobo.com/en/portal/fee-station/introduction).
* Added the following operations to support token listing via self-service submission:
  * [Create token listing request](/developers/v2/api-references/wallets/create-token-listing-request)
  * [List token listing requests](/developers/v2/api-references/wallets/list-token-listing-requests)
  * [Get token listing request](/developers/v2/api-references/wallets/get-token-listing-request)

### Improvements

* Added new [webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types) to support more real-time updates:
  * `wallets.token_listing.failed`
  * `wallets.token_listing.succeeded`
  * `payment.transaction.created`
  * `payment.transaction.late`
  * `payment.transaction.held`
  * `payment.status.updated`
  * `payment.refund.status.updated`
  * `payment.settlement.status.updated`

* Added new fields `wallet_type` and `wallet_sub_type` to the `wallet.token.enabled` and `wallet.chain.enabled` webhook events to indicate supported wallet types and sub-types.

* Enhanced the [List Fee Station token balances](/developers/v2/api-references/feestation/list-fee-station-token-balances) operation by adding the `chain_id` field to the response.

* Enhanced the [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation. By default, it now returns transactions from the past 90 days if `min_created_timestamp` and `max_created_timestamp` are not specified.

## v1.13.0

This version was released on April 9, 2025.

### Breaking Changes

* The `name` property is now required in the [Update wallet](/developers/v2/api-references/wallets/update-wallet) operation.
* The `AddressEncoding` field now returns `ENCODING_DEFAULT` instead of an empty string ("") as the default value.

### Improvements

* Added a new schema `CustodialWeb3TransferSource` to support Replace-By-Fee (RBF) transactions from Custodial Wallets (Web3 Wallets). You can now initiate RBF transactions from Custodial Wallets (Web3 Wallets) using the [Drop transaction](/developers/v2/api-references/transactions/drop-transaction) and [Speed up transaction](/developers/v2/api-references/transactions/speed-up-transaction) operations.

* Added the following new transaction [sub-statuses](/developers/v2/guides/transactions/status) to provide more granular tracking of transaction progress:
  * `PendingSignerApproval`
  * `PendingSignerProcessing`
  * `RejectedBySigner`
  * `FailedSignerTimeout`
  * `InsufficientBalance`
  * `InsufficientBalanceFundLocked`
  * `PendingSystemProcessing`
  * `SystemProcessingOngoing`
  * `ReOrged`

* Added new schemas `TransactionBIP137Destination`, `TransactionBIP322Destination`, `TransactionCosmosAdr36Destination`, and `TransactionMessageSignBTCEIP191Destination`. You can now [sign messages](/developers/v2/api-references/transactions/sign-message) and [view transactions](/developers/v2/api-references/transactions/list-all-transactions) using these destination types.

* Extended the `AddressEncoding` schema with new enum values `ENCODING_ADA_BYRON`, `ENCODING_ADA_SHELLEY`, and `ENCODING_DEFAULT` to support a wider range of address encoding formats.

* Introduced a new `extra` property in the `Transaction` schema to carry structured, extensible, and business-specific information. This field is returned as a JSON-encoded string.

* Removed the properties `param_version`, `withdraw_from_type`, `slash_from_type`, and `stake_amount` from the `BabylonStakingActivityDetailExtra` schema.

## v1.12.0

This version was released on March 27, 2025.

### New Features

Now you can query Fee Station information with the following operations:

* [Get Fee Station transaction information](/developers/v2/api-references/feestation/get-fee-station-transaction-information)
* [List all Fee Station transactions](/developers/v2/api-references/feestation/list-all-fee-station-transactions)
* [List Fee Station addresses](/developers/v2/api-references/feestation/list-fee-station-addresses)
* [List Fee Station token balances](/developers/v2/api-references/feestation/list-fee-station-token-balances)

Additionally, we've introduced a new operation to update wallet balances:

* [Refresh address balances by token](/developers/v2/api-references/wallets/refresh-address-balances-by-token)

### Improvements

* Added support for Custodial Wallets (Web3 Wallets) across key transaction operations.
  * You can set `Web3` as the transaction source in the following operations:
    * [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee)
    * [Transfer token](/developers/v2/api-references/transactions/transfer-token)
    * [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract)
    * [Sign message](/developers/v2/api-references/transactions/sign-message)

  * You can also query transactions originating from the `Web3` transaction source in the following query operations:
    * [List all transactions](/developers/v2/api-references/transactions/list-all-transactions)
    * [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information)

* Added new webhook event types `wallet.token.enabled` and `wallet.chain.enabled`, along with new data types `Tokens` and `Chains`. For more details, refer to [Webhook event types and data types](/developers/v2/guides/webhooks-callbacks/webhook-event-type).

* Extended schema properties:
  * `TransactionMessageSignEIP712Destination`: Added `safe_tx_extra_data` and `raw_structured_data` for enhanced Safe transaction context
  * `BabylonStakingActivityDetailExtra`: Added `withdraw_from_type` and `slash_from_type` for improved Babylon staking activity information
  * `Transaction`: Added `cobo_category` for Cobo-defined transaction categorization
  * `TransactionSelectedUtxo`: Added `redeem_script` and `revealed_script` for detailed UTXO transaction information

* Optimized `TransactionUtxoFee` schema by making `fee_rate` an optional field

* The [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation now supports sorting by direction.

## v1.11.0

This version was released on March 12, 2025.

### Improvements

* Added support for Solana (SOL) contracts in the [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract) operation.
* Added the `reserved_fee` property to the response of the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) operation for both EIP-1559 and legacy fee models, which represents the estimated fee for submitting transaction calldata to L1 (Layer 1).

## v1.10.0

This version was released on March 3, 2025.

### New Features

Now you can initiate and track registration for Babylon airdrop and Babylon Phase-2 with the following operations:

* [List wallets eligible for Babylon airdrop](/developers/v2/api-references/stakings/list-wallets-eligible-for-babylon-airdrop)
* [Register for Babylon airdrop](/developers/v2/api-references/stakings/register-for-babylon-airdrop)
* [List Babylon airdrop registrations](/developers/v2/api-references/stakings/list-babylon-airdrop-registrations)
* [Get Babylon airdrop registration details](/developers/v2/api-references/stakings/get-babylon-airdrop-registration-details)
* [List staking positions eligible for Babylon Phase-2](/developers/v2/api-references/stakings/list-staking-positions-eligible-for-babylon-phase-2)
* [Register for Babylon Phase-2](/developers/v2/api-references/stakings/register-for-babylon-phase-2)
* [List Babylon Phase-2 registrations](/developers/v2/api-references/stakings/list-babylon-phase-2-registrations)
* [Get Babylon Phase-2 registration details](/developers/v2/api-references/stakings/get-babylon-phase-2-registration-details)

### Improvements

* Added a `utxo_change` property with UTXO change information to the `TransactionRawTxInfo` schema.
* Added 3 enum values `BitHive`, `BERABeacon`, and `BeraChainBGT` to the `StakingPoolType` schema.
* Added 6 enum values `bithive_signet`, `bithive`, `beacon_bera`, `beacon_bera_testnet`, `berachain_bgt`, and `berachain_bgt_testnet` to the `StakingPoolId` schema.
* Added a property `wallet_id` to the `AddressesEventData` schema.
* Added a property `mpc_used_key_share_holder_group` to the `MpcContractCallSource`, `MpcMessageSignSource`, and `MpcTransferSource` schemas to indicate which key share holder group is used for this transaction.

## v1.9.0

This version was released on February 19, 2025.

### New Features

* Added [List address balances by token](/developers/v2/api-references/wallets/list-address-balances-by-token) operation for MPC Wallets to retrieve token balances across multiple addresses.
* Enhanced MPC Wallet key share holder management with new operations:
  * [Get key share holder information](/developers/v2/api-references/wallets--mpc-wallets/get-key-share-holder-information): Retrieve detailed information about specific key share holders.
  * [List all key share holders](/developers/v2/api-references/wallets--mpc-wallets/list-all-key-share-holders): Get a comprehensive list of all key share holders.
* Added the [Sign and broadcast transaction](/developers/v2/api-references/transactions/sign-and-broadcast-transaction) operation, along with the `Built` transaction sub-status and the `unsigned_raw_tx` property in the `raw_tx_info` object of the `Transaction` schema, to manually sign and broadcast transactions that were built without being executed automatically.

### Improvements

* Enhanced the [List UTXOs](/developers/v2/api-references/wallets/list-utxos) operation with a new `tx_hash` query parameter, enabling UTXO lookup by transaction hash.
* Enhanced the [Sign message](/developers/v2/api-references/transactions/sign-message) operation to support raw message and BTC EIP-191 signature.
* Enhanced the [Create addresses in wallet](/developers/v2/api-references/wallets/create-addresses-in-wallet) operation to enable generating tweaked addresses.
* Enhanced the [Transfer token](/developers/v2/api-references/transactions/transfer-token) operation by adding a new property `change_output_type` to the `AddressTransferDestination` schema.
* Added a `tx_info` property to the `TransactionDepositToAddressDestination` schema, including `vout_n` index information.

## v1.8.0

This version was released on January 8, 2025.

### New Features

* Added Travel Rule operations:
  * [Submit Travel Rule information for deposits](/developers/v2/api-references/travelrule/submit-travel-rule-information-for-deposits)
  * [Submit Travel Rule information for withdrawals](/developers/v2/api-references/travelrule/submit-travel-rule-information-for-withdrawals)
  * [Retrieve transaction limitations](/developers/v2/api-references/travelrule/retrieve-transaction-limitations)
  * [List supported countries](/developers/v2/api-references/travelrule/list-supported-countries)
* Added support for Sky Farm staking protocol.
* Added the [List all callback messages](/developers/v2/api-references/developers/list-all-callback-messages) and [Retry callback message](/developers/v2/api-references/developers/retry-callback-message) operations for efficient management on callback messages.

### Improvements

* Added new [webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type#webhook-event-types) `wallets.addresses.created`, `wallets.created`, and `mpc_vaults.created` and new event data types `Addresses`, `WalletInfo`, and `MPCVault` to optimize the processing of webhook events.
* Made several improvements to staking operations:
  * Added the `BabylonStakingActivityDetailExtra`, `EthStakingActivityDetailExtra`, and `CoreStakingActivityDetailExtra` schemas to represent the extra details for each staking protocol.
  * Added the `request_id` query parameter for the [List staking activities](/developers/v2/api-references/stakings/list-staking-activities) operation to filter activities based on a specific request ID.
  * Made the `extra` property optional in the `CreateStakeActivity` schema.
* Added the `root_pubkey` property to the `AddressInfo` schema to indicate the root extended public key of the address.
* Added the `TransactionSelectedUtxo` schema to represent the selected UTXO information in a transaction.

## v1.7.0

This version was released on December 19, 2024.

### Breaking Changes

* Renamed `create_timestamp` to `created_timestamp` in the `MPCProject` schema to improve consistency in naming conventions.

### New features

* Added the [Create claim activity](/developers/v2/api-references/stakings/create-claim-activity) operation for claiming staking rewards.
* Added a new version of the [Estimate staking fees](/developers/v2/api-references/stakings/estimate-staking-fees-v2) operation with improved functionality.
* Added support for staking in the CORE protocol.
* Added the `auto_fuel` property to the request payloads of the following operations to enable the use of [Fee Station](https://manuals.cobo.com/en/portal/fee-station/introduction) for automatic transaction fee payment:
  * [Transfer token](/developers/v2/api-references/transactions/transfer-token)
  * [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract)
  * [Speed up transaction](/developers/v2/api-references/transactions/speed-up-transaction)
  * [Drop transaction](/developers/v2/api-references/transactions/drop-transaction)

### Improvements

* Made several fields optional in the `BabylonValidator` schema.
* Extended ETH staking functionality by adding the `beacon_validators` property to the `EthStakingExtra` schema to represent the list of validator information.
* Improved the `StakingPoolId` schema by making it an enum type.
* Extended the `ActivityAction` schema with additional enums to cover more actions that can occur during a staking activity.
* Deprecated the original version of the "Estimate staking fees" operation.

## v1.6.0

This version was released on November 13, 2024.

### Breaking changes

* Removed the "Get address information" operation.
* Made `amount` a required property in the `AddressTransferDestination` schema.

### New features

* Added the following new operations:
  * [Get API key information](/developers/v2/api-references/developers/get-api-key-information): Retrieve details of your API key.
  * [Check address validity across chains](/developers/v2/api-references/wallets/check-address-validity-across-chains): Validate addresses across multiple chains.
* Added support for Ethereum staking.

### Improvements

* Made the following properties optional:
  * `request_id` and `destination` in `EstimateTransferFeeParams`
  * `request_id` in `EstimateContractCallFeeParams`
* Removed the `script` property from:
  * `TransactionTransferToAddressDestination`
  * `AddressTransferDestination`

## v1.5.0

This version was released on October 24, 2024.

### Breaking Changes

In this release, the following parameter names in the [Python SDK](https://github.com/CoboGlobal/cobo-waas2-python-sdk/) have been updated:

* `ORG_MINUS_CONTROLLED` → `ORG_CONTROLLED`
* `USER_MINUS_CONTROLLED` → `USER_CONTROLLED`
* `SAFE_LEFT_CURLY_BRACKET_WALLET_RIGHT_CURLY_BRACKET` → `SAFE_WALLET`

Please update your code to reflect these changes, as previous parameter names are no longer supported.

### New features

* Added the List Delegates operation for Smart Contract Wallets. (This operation has since been retired.)
* Added the [List address book entries](/developers/v2/api-references/addressbooks/list-address-book-entries) operation to retrieve addresses from your address book.
* Added the [Trigger test event](/developers/v2/api-references/developers--webhooks/trigger-test-event) operation to test the functionality of your webhook endpoint.

### Improvements

* Added the `asset_model_type` property in the response of the [Get token information](/developers/v2/api-references/wallets/get-token-information) operation to indicate whether a token uses the account model or the UTXO model.
* Added the `calldata_info` property to the `TransactionEvmContractDestination` schema to provide a more detailed representation of smart contract calldata.
* Added the `TransactionRawMessageSignDestination` schema and added the `Raw_Message_Signature` value to the `destination_type` enum to represent the transaction destination for raw message signatures.
* Added `Stake` and `Unstake` as new possible values for the `types` query parameter in the [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation.
* Added `bitmart` and `bitfinex` as new possible values to the `exchange_id` enum.
* The `delegate` property is no longer a required property in the `TransactionSmartContractSafeWalletSource` schema.

## v1.4.0

This version was released on September 25, 2024.

### Improvements

* Improved the tracking of transactions by adding and removing certain statuses and sub-statuses in the `TransactionStatus` and `TransactionSubStatus` schemas.
* Added the `MPCProcessing` status in the `TSSRequestStatus` schema to indicate that the TSS request approval is waiting to be started.
* Removed the `nonce` property in the `MpcContractCallSource` schema.

## v1.3.0

This version was released on September 12, 2024.

### New features

* You can now stake your tokens with the WaaS 2.0 API. Staking operations include:
  * [List staking positions](/developers/v2/api-references/stakings/list-staking-positions)
  * [Get staking position details](/developers/v2/api-references/stakings/get-staking-position-details)
  * [List staking activities](/developers/v2/api-references/stakings/list-staking-activities)
  * [Estimate staking fees](/developers/v2/api-references/stakings/estimate-staking-fees)
  * [Create stake activity](/developers/v2/api-references/stakings/create-stake-activity)
  * [Create unstake activity](/developers/v2/api-references/stakings/create-unstake-activity)
  * [Create withdraw activity](/developers/v2/api-references/stakings/create-withdraw-activity)
  * [Get staking activity details](/developers/v2/api-references/stakings/get-staking-activity-details)
  * [List staking pools](/developers/v2/api-references/stakings/list-staking-pools)
  * [Get staking pool details](/developers/v2/api-references/stakings/get-staking-pool-details)
* Added the [Broadcast signed transactions](/developers/v2/api-references/transactions/broadcast-signed-transactions) operation to broadcast signed transactions.

### Improvements

* Changed the path of the [Check Cobo Loop transfers](/developers/v2/api-references/transactions/check-cobo-loop-transfers) operation from `/wallets/check_loop_transfers` to `/transactions/check_loop_transfers`.
* Added the `dust_threshold` and `custodial_minimum_deposit_threshold` properties in the `TokenInfo` schema to indicate the minimum withdrawal and deposit amounts for Custodial Wallets.
* Added the `confirming_threshold` property in the `ChainInfo` schema to indicate the number of confirmations required for a transaction on each chain.

### Bug fixes

* Fixed an issue with using WaaS SDKs to perform operations relating to contract call or message signing.

## v1.2.0

This version was released on August 21, 2024.

### New features

* Added support for [Exchange Wallets](https://manuals.cobo.com/en/portal/exchange-wallets/introduction) and Smart Contract Wallets. Added the following operations for Exchange Wallets:
  * [List supported exchanges](/developers/v2/api-references/wallets--exchange-wallet/list-supported-exchanges)
  * [List supported assets](/developers/v2/api-references/wallets--exchange-wallet/list-supported-assets)
  * [List supported chains](/developers/v2/api-references/wallets--exchange-wallet/list-supported-chains)
  * [List asset balances](/developers/v2/api-references/wallets--exchange-wallet/list-asset-balances)
* Added the following operations for batch payment:
  * [Check addresses validity](/developers/v2/api-references/wallets/check-addresses-validity)
  * [Check Cobo Loop transfers](/developers/v2/api-references/transactions/check-cobo-loop-transfers)
* You can now subscribe to TSS request-related event types for your webhook endpoints. For more information about TSS request-related event types, refer to [Webhook event types and data types](/developers/v2/guides/webhooks-callbacks/webhook-event-type).

### Improvements

* The `sub_wallet_id` property was renamed as `trading_account_type`. Affected schemas include:
  * `ExchangeTransferSource`
  * `ExchangeTransferDestination`
  * `TransactionTransferToWalletDestination`
  * `TransactionExchangeWalletSource`
  * `TransactionDepositFromWalletSource`
  * `TransactionDepositToWalletDestination`
* Added the `PendingApprovalStart` enum value in the `TransactionSubStatus` enum to indicate a status that requires specific action from users for proceeding with the transaction.
* Added the `project_name` and `vault_name` properties in the `MPCWalletInfo` schema to indicate the project name and vault name.
* Added the `description` and `created_timestamp` properties in the `TSSRequest` schema to indicate the description and creation time of the TSS request.
* Added the `account_id` property in the `KeyShareHolder` schema to indicate the key share holder’s account ID on Cobo Portal.
* Added the `signer_key_share_holder_group_id` property in the `TransactionMPCWalletSource` schema to indicate the ID of the key share holder group as the transaction signer.
* Added the `description` property in the request body of [Create TSS request](/developers/v2/api-references/wallets--mpc-wallets/create-tss-request) to indicate the description of the TSS request.

## v1.1.0

This version was released on August 7, 2024.

### New features

Added OAuth operations for Cobo Portal App developers:

* [Get access token](/developers/v2/api-references/oauth/get-org-access-token)
* [Refresh access token](/developers/v2/api-references/oauth/refresh-org-access-token)

### Improvements

* The data type of `data.response_body` was updated from object to string in the response of [List webhook event logs](/developers/v2/api-references/developers--webhooks/list-webhook-event-logs).
* Added the `signer` property to indicate whether the key share holder's TSS Node is a designated transaction signer. Affected schemas include:
  * `CreateKeyShareHolder`
  * `KeyShareHolder`
* The `node_count` property was renamed as `participants` in:
  * The request body of [Create project](/developers/v2/api-references/wallets--mpc-wallets/create-project)
  * The request body of [Create key share holder group](/developers/v2/api-references/wallets--mpc-wallets/create-key-share-holder-group)
  * The `KeyShareHolderGroup` schema
  * The `MPCProject` schema
* The `pubkey` property was renamed as `root_pubkey` in the `RootPubkey` schema.
* Added the `root_pubkey` property to indicate the vault's root extended public key in the `TSSGroups` schema.
* Several timestamp-related properties were renamed using the “\_timestamp” suffix. Affected schemas include:
  * `Transaction`
  * `TransactionBlockInfo`
  * `TransactionTimeline`
  * `KeyShareHolderGroup`
  * `MPCVault`

## v1.0.0

This is the first release of the Cobo WaaS 2.0 API.

This release includes support for [Custodial Wallets](https://manuals.cobo.com/en/portal/custodial-wallets/introduction) and [MPC Wallets](https://manuals.cobo.com/en/portal/mpc-wallets/introduction), with the following categories of operations:

* [General wallet operations](/developers/v2/api-references/wallets/list-supported-chains)
* [MPC Wallets-specific operations](/developers/v2/api-references/wallets--mpc-wallets/list-all-cobo-key-share-holders)
* [Transactions operations](/developers/v2/api-references/transactions/estimate-transaction-fee)
* [Webhook operations](/developers/v2/api-references/developers--webhooks/list-webhook-endpoints)


# Authentication
Source: https://cobo.com/developers/v2/guides/overview/cobo-auth

Guide to authenticating API requests to the WaaS service using Cobo Auth, including API key and signature details.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This article explains how to authenticate your API requests to the WaaS service using Cobo Auth.

To ensure secure access to your crypto assets, the WaaS service requires you to use an EdDSA signature to sign each of your API requests, except for publicly accessible API operations.

You need to provide your API key, a nonce, and an API signature as request headers:

```
headers = {
  "Biz-Api-Key": {YOUR_API_KEY}.hex(),
  "Biz-Api-Nonce": {Nonce},
  "Biz-Api-Signature": {YOUR_API_SIGNATURE}.hex(),
}
```

* Biz-Api-Key: The API key used for the request. For more details, refer to [API key](#api-key).
* Biz-Api-Nonce: A random string used as the request nonce.
* Biz-Api-Signature: The API signature. To learn how to calculate an API signature, see [Calculate an API Signature](#calculate-the-api-signature).

If you are using Cobo's WaaS SDKs, you only need to provide your API secret because the SDKs handles the remaining steps for you.

## API key and API secret

To enable secure and authenticated communication between clients and the WaaS 2.0 service, a mechanism based on the API key and API secret is used.  This mechanism relies on cryptographic key pairs to verify the identity of the client and the integrity of the requests.

### API key

The API key is the public key in the cryptographic key pair. It is used to identify the client making the API request.

The API key is associated with permissions and wallet scopes, which define the actions the client can perform and the wallets they can access. Different API keys can be assigned with varying permissions and wallet scopes, providing granular control over client capabilities.
<Info>For more details about permissions and wallet scopes, see [Permissions and wallet scopes](/developers/v2/guides/overview/permissions-and-scopes).</Info>

### API secret

The API secret is the private key in the key pair. It is used to sign API requests, guaranteeing their authenticity and integrity. The API secret must always remain confidential and secure to prevent unauthorized access.

The API key and API secret work as a pair to secure communication with the WaaS 2.0 service:

* The API key is included in API requests to identify the client to the WaaS service. It is required to be registered on Cobo Portal. For more information, refer to [Register an API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key).
* The API secret is used to generate a signature for each API request. The WaaS service validates the signature to confirm the request’s authenticity and prevent tampering.

### Generate an API key and an API secret

This section introduces three ways to generate an API key and an API secret using the Ed25519 algorithm. You can also generate them using other tools that use the Ed25519 algorithm.

The public key will be used as an API key, and the private key will be used as an API secret.

#### Use Cobo CLI

Cobo Command Line Interface (CLI) is a powerful developer tool designed to help you build, test, and manage your integration with Cobo Wallet-as-a-Service (WaaS) 2.0 directly from the command line.

1. Install Cobo CLI using the following command:

   ```shell theme={null}
   # Install Cobo CLI using pip (Python 3.9 or newer is required).
   pip install cobo-cli
   # Alternatively, you can install Cobo CLI using Homebrew.
   brew install cobo-cli
   # Test if the installation is successful
   cobo version
   ```

   For more details about the system requirements for Cobo CLI, please refer to [Install Cobo CLI](/developers/v2/developer-tools/cobo-cli/quick-start-guide#system-requirements).

2. Use the `keys generate` command to generate a key pair using the Ed25519 algorithm as follows:

   ```shell theme={null}
   # Generate an API key and an API secret
   cobo keys generate --key-type API
   ```

   Generated keys are securely stored in your configuration file (default: `~/.cobo/config.toml`). For more information about this command, refer to [Key management](/developers/v2/developer-tools/cobo-cli/key-management).

#### Use OpenSSL

In a terminal window, run the following OpenSSL commands to generate a key pair using the Ed25519 algorithm:

```shell theme={null}
openssl genpkey -algorithm ed25519 -out private_key.pem

openssl pkey -in private_key.pem -pubout -out public_key.pem

echo "Private Key (Hex):"
openssl pkey -in private_key.pem -text | grep 'priv:' -A 3 | tail -n +2 | tr -d ':\n ' && echo

echo "Public Key (Hex):"
openssl pkey -pubin -in public_key.pem -text | grep 'pub:' -A 3 | tail -n +2 | tr -d ':\n ' && echo
```

You will see the output similar to the following example:

```
Private Key (Hex):
06f78882576ec0e05b1e51a33548da7e8cf958c190ba96be77b1c671f98a2b5f
Public Key (Hex):
5987dedc180167b7ab1d27e6009e5065d10d764cd85d7b64f8c968ca40326e28
```

Use the `Private Key (Hex)` as your API secret and the `Public Key (Hex)` as your API key.

#### Use the Python library

1. Install the `PyNaCl` Python library.

   In a terminal window, run the following command:

   ```shell theme={null}
   pip install PyNaCl
   ```

2. Generate a key pair.
   Import the function from the Python library to generate a key pair using the Ed25519 algorithm as follows:

   ```python theme={null}
   from nacl.signing import SigningKey
   # Create a key pair.
   sk = SigningKey.generate()
   # Print the private key in hexadecimal format.
   print("private key:", sk.encode().hex())
   # Print the public key in hexadecimal format.
   print("public key:", sk.verify_key.encode().hex())
   ```

### Register the API key

After generating an API key, you need to register the key and configure related permissions on Cobo Portal. To learn how to register an API key, see [Register an API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key).

<Warning>
  The Development and Production environments use **separate Cobo Portals with separate API keys**. An API key registered in the Development environment (`portal.dev.cobo.com`) cannot authenticate requests to the Production host (`api.cobo.com`), and vice versa. Using a key from the wrong environment returns HTTP 401 / error code 2024 with the message `Your API key is not registered in this environment. Development and Production environments use separate API keys.` See [Development and production environments](/developers/v2/guides/overview/environments) for host URLs and portal addresses.
</Warning>

## Nonce

In WaaS 2.0 authentication, Nonce refers to the value of the `Biz-Api-Nonce` request header. This can be any random string.

## Calculate the API signature

The following steps introduce how to calculate an API signature.

1. First, concatenate a string based on your request as follows:

   str\_to\_sign = `{METHOD}|{PATH}|{NONCE}|{PARAMS}|{BODY}`

   | **Field** | **Description**                                                                                 | **Example**                                                             |
   | --------- | ----------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------- |
   | METHOD    | The HTTP method.                                                                                | `GET`                                                                   |
   | PATH      | The API endpoint.                                                                               | `/v2/transactions/transfer`                                             |
   | NONCE     | The nonce value. This value must exactly match the value of the `Biz-Api-Nonce` request header. | `1718587017026`                                                         |
   | PARAMS    | (If applicable) The query parameters.                                                           | `chain_id=ETH&limit=10`                                                 |
   | BODY      | (If applicable) The raw request body in string format.                                          | `{"name":"Default","wallet_subtype":"Asset","wallet_type":"Custodial"}` |

2. Use the `hashlib` library to perform SHA-256 hashing twice on the string as follows:

   ```python theme={null}
   import hashlib
   content_hash = hashlib.sha256(hashlib.sha256(str_to_sign.encode()).digest()).digest()
   ```

3. Use the API secret to sign the string as follows:

   ```python theme={null}
   from nacl.signing import SigningKey

   # Create an Ed25519 signing key. Replace `api_secret` with your API secret.
   sk = SigningKey(bytes.fromhex(api_secret))
   # Sign the hashed message
   signature = sk.sign(content_hash).signature.hex()
   ```

Now you've calculated an API signature.


# Cobo WaaS Skill
Source: https://cobo.com/developers/v2/guides/overview/cobo-waas-skill



As a developer, you can use Cobo WaaS Skill with Claude Code, Cursor, or other familiar AI coding assistants to interact with the [Cobo WaaS 2.0 API](/developers/v2/guides/overview/introduction) via natural language, or to generate SDK invocation code for your applications.

## Example project

The video below showcases a web wallet application that was built from the ground up using the Cobo WaaS Skill in 30 minutes:

<video>
  <source type="video/mp4" />

  Your browser does not support the video tag.
</video>

Key prompt examples include:

* "Help me build an app where users can create wallets and generate addresses on blockchain networks like BTC, ETH, or TRON"
* "Update the frontend to include wallet type selection"
* "For each wallet, get the balance and display it accordingly"
* "Allow users to transfer tokens out of a selected wallet"

### Key Features

Cobo WaaS Skill is a set of commands, reference documents, code examples, and best practices that enable:

* **SDK code generation** – Describe your business requirements in natural language, and the Skill will generate production-ready SDK code in Python, Node.js, Go, or Java.
* **Debugging and troubleshooting** – Intelligently monitor and troubleshoot issues with your API calls.
* **Comprehensive CLI toolkit** – Execute all WaaS API operations plus developer utilities including API key management, webhook testing, and GraphQL queries.

## Getting started

### Prerequisites

* Python 3.9 or higher
* Claude Code or Cursor installed
* Cobo Portal account

### Installation

Install the Cobo CLI and the WaaS Skill:

```bash theme={null}
# Install Cobo CLI
pip install cobo-cli

# Install Skill for Claude Code
cobo skill install claude

# Or for Cursor
cobo skill install cursor

# Install Skill for all supported AI assistants in the current project directory
cobo skill install all --scope local

# Verify installation
cobo skill status
```

<Note>If you have already installed Cobo CLI, you must upgrade to version **0.1.1** or above to use the Cobo WaaS Skill. Run `pip install --upgrade cobo-cli` to upgrade.</Note>

### Starting your first WaaS operation

Once installed, you can use natural language in your AI assistant to perform WaaS operations. Here's an example of setting up and making your first API call:

<Tip>For best results, explicitly mention the skill by prefixing your prompt with `/cobo-waas` or including "Use Cobo WaaS skill" in your request.</Tip>

**What you ask your AI assistant:**

```
"/cobo-waas set up the dev environment and list my wallets"
```

Or:

```
"Use Cobo WaaS skill to set up the dev environment and list my wallets"
```

**What the AI assistant does:**

```bash theme={null}
# === Dev environment ===
cobo env dev
cobo login -u                        # OAuth login, opens browser automatically

# Generate and auto-register API Key
cobo keys generate --key-type API
cobo keys register                   # Auto-registration supported in dev environment

# Test API connectivity
cobo get /wallets --limit 10


# === Prod environment ===
cobo env prod

# Generate API key pair
cobo keys generate --key-type API
cobo open developer                  # Open developer console to register public key manually

# Configure authentication
cobo auth apikey

# Test API connectivity
cobo get /wallets --limit 10
```

### Example commands

Here are examples of natural language requests you can make:

**For CLI Operations:**

* **"Create an Asset Wallet named 'Treasury' and generate an Ethereum address"**
* **"Execute a transfer of 0.01 ETH from wallet f47ac10b-... to address 0x1234..."**
* **"Trigger a test webhook event for transaction success"**

**For Vibe Coding (SDK Generation):**

* **"Generate Python code to create a wallet and poll for transaction completion"**
* **"Write Node.js code for a webhook handler that processes transaction events"**
* **"Generate Python code for an Exchange app that creates deposit addresses for each user"**

The AI assistant will execute the appropriate CLI commands, handle errors, and provide structured feedback at each step. For SDK generation requests, it produces production-ready code in your chosen language.

## Next steps

You can refer to the following documents to learn more about Cobo WaaS API integration:

* [Cobo CLI Documentation](/developers/v2/developer-tools/cobo-cli/introduction) - Complete CLI reference and commands
* [WaaS 2.0 API Reference](/developers/v2/api-references) - Full API endpoint documentation
* [Cobo WaaS 2.0 Overview](/developers/v2/guides/overview/introduction) - Platform concepts and architecture


# Development and production environments
Source: https://cobo.com/developers/v2/guides/overview/environments

Overview of WaaS 2.0 API environments for development and production, including purposes and URLs.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

The WaaS 2.0 API provides two environments serving different purposes. It is recommended that you use the development environment to test your new features first before deploying them to the production environment.
Direct registration for a free trial grants you immediate access to the Production Environment. There is no need to switch to the development environment; both your integration testing and official usage will be conducted within the production environment.

|                 | **Development environment**                                                                                                   | **Production environment**                                                                                                     |
| --------------- | ----------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------ |
| Purpose         | Used for developing, testing, and debugging new features and functionality without impacting the live, production environment | The live, customer-facing environment that users interact with                                                                 |
| API base URL    | [https://api.dev.cobo.com/v2](https://api.dev.cobo.com/v2)                                                                    | [https://api.cobo.com/v2](https://api.cobo.com/v2)                                                                             |
| Cobo Portal URL | [https://portal.dev.cobo.com/](https://portal.dev.cobo.com/)                                                                  | [https://portal.cobo.com/](https://portal.cobo.com/)                                                                           |
| Testnets        | Supported                                                                                                                     | Supported                                                                                                                      |
| Pricing         | Free to use                                                                                                                   | Paid. For details, see [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction). |

<Warning>
  API keys are **environment-specific**. Keys registered in the Development environment (`portal.dev.cobo.com`) are only valid for the Development API host (`api.dev.cobo.com`), and keys registered in the Production environment (`portal.cobo.com`) are only valid for the Production API host (`api.cobo.com`). Using a key from the wrong environment returns HTTP 401 / error code 2024 with the message `Your API key is not registered in this environment. Development and Production environments use separate API keys.` Register your API key in the matching Cobo Portal for the environment you are calling.
</Warning>


# Error codes and status codes
Source: https://cobo.com/developers/v2/guides/overview/error-codes

List of error codes for the WaaS 2.0 API, with explanations and troubleshooting tips.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This article explains the common error codes and HTTP status codes you may encounter when using the Cobo WaaS 2.0 API and how to resolve the errors.

### Error codes

#### General errors

| Error code | Description                                                                                                                          | Solution                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                             |
| ---------- | ------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 1000       | Internal Server Error. This error can be caused by several issues including expired [Org Access Tokens](/developers/v2/apps/org-access-tokens). | Check your server configuration settings, including whether your Org Access Token has expired, and try again later.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| 1003, 2003 | One or more required parameters are missing in the request.                                                                          | The `error_message` field names the specific missing parameter. Identify that parameter, confirm which parameters are required in the API reference for the operation you are calling, add it, and retry.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| 1006, 2006 | One or more parameters are in an invalid format or contain unsupported values.                                                       | The `error_message` field names the parameter that failed validation. Check the API reference for the operation you are calling to confirm the expected type, format, and allowed values for that parameter, then correct the value and retry.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       |
| 2000       | Internal error occurred during processing.                                                                                           | This is a temporary error on Cobo's side. Retry after a short delay. If the error persists, contact Cobo support at [help@cobo.com](mailto:help@cobo.com) and provide the `error_id` from the response so the failure can be traced.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 |
| 2021       | The requested API endpoint is not implemented or is currently unavailable.                                                           | Confirm the request path and HTTP method exactly match the operation in the API reference (a trailing slash or wrong method also returns this error). If they are correct, the endpoint may be temporarily unavailable — retry after a short delay using exponential backoff.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        |
| 2024       | API key authentication failed.                                                                                                       | <ul><li>If `error_message` is `Your API key is not registered in this environment...`: you are using a key registered in the wrong environment. Switch to the correct API host and use the matching API key. See [Environments](/developers/v2/guides/overview/environments).</li><li>If `error_message` is `Your API key is not yet activated...` or `Api key is not activated`: complete Admin approval in Cobo Guard for the key to become Active.</li><li>If `error_message` mentions the IP whitelist: add your server's egress IP to the key's allowlist in Cobo Portal.</li><li>For signature failures, ensure the canonical string follows the format `METHOD\|PATH\|NONCE\|PARAMS\|BODY` with the nonce identical to the `Biz-Api-Nonce` header. See [Authentication](/developers/v2/guides/overview/cobo-auth).</li></ul>For details, see <a href="https://manuals.cobo.com/en/portal/developer-console/create-api-key">Register an API Key</a>.                                                                                                                                                                                                                                                                                                                                                                                                 |
| 2025, 4001 | Forbidden access to the requested resource.                                                                                          | <ul><li>Check the permissions, wallet scopes, and resource scopes associated with your API key. You can refer to [Permissions and wallet scopes](/developers/v2/guides/overview/permissions-and-scopes) for details.</li><li>If the error is related to user roles (for example, creating withdrawals or initiating transactions), make sure the operator has the required role (for example, withdrawals typically require Spender or Admin).</li><li>If the error message contains "Resource out of organization (4001)", it usually means the resource you are accessing (for example, `wallet_id`) belongs to a different organization than the API key.</li><li>If you have granted permissions but still get forbidden, check whether you are mixing Dev/Prod API keys or calling the wrong environment domain.</li><li>For Custodial Wallet operations, verify that the permission is granted at the correct (upper) scope level (some permissions must be enabled in the parent Custodial Wallet settings).</li><li>If this operation requires an enabled capability (feature flag / allowlist), ensure it is enabled in the target environment.</li><li>If this is chain/asset related (for example, adding a chain but still seeing forbidden), confirm the chain/capability is enabled in your pricing plan/configuration.</li></ul> |
| 2026       | Too many requests.                                                                                                                   | Reduce your request frequency and retry after a short delay. For polling or batch patterns, implement exponential backoff — for example, start with a 1-second delay and double it on each retry (1s, 2s, 4s, ...) up to a maximum.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| 2028       | The requested resource was not found.                                                                                                | The resource ID does not exist in your organization or was created in a different environment. List the relevant resources to confirm the correct ID (for example, call [List transactions](/developers/v2/api-references/transactions/list-transactions) for a `transaction_id`), then retry with a valid ID. Confirm you are calling the same environment (Development or Production) in which the resource was created.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 2029       | The value provided for the `status` parameter is not one of the allowed values.                                                      | The allowed values for `status` depend on the operation (for example, transaction status differs from screening status). In the API reference, open the operation you are calling and provide one of the `status` enum values listed for its request parameters.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     |
| 10000      | This organization has read-only permissions in Cobo Portal.                                                                          | Your organization currently has read-only access, so write operations are rejected. A team admin must log in to Cobo Portal and review the organization's access status in the organization settings; only a team admin can change the access level. Members without the admin role cannot change this setting.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |

#### Pricing plan errors

| Error code | Description                                                                                                 | Solution                                                                                                                                                                                                                                                     |
| ---------- | ----------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 2050       | No pricing plan is active for this organization, so billable API operations are blocked.                    | Activate a pricing plan: log in to Cobo Portal, open **Bills & Payments**, and select a plan. For more information, see [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction).                              |
| 2051       | The organization's pricing plan has expired, so billable operations are blocked until it is renewed.        | Renew your pricing plan: in Cobo Portal, open **Bills & Payments** and renew or select a plan. For more information, see [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction).                             |
| 2052       | The organization has exceeded the usage quota included in its current pricing plan.                         | Wait for the next billing cycle to reset the quota, or upgrade to a higher plan in Cobo Portal under **Bills & Payments**. For more information, see [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction). |
| 2053       | The current pricing plan does not include the entitlement required for this operation.                      | Upgrade to a plan that includes this feature in Cobo Portal under **Bills & Payments**. For more information, see [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction).                                    |
| 2054       | Payment for the current pricing plan is overdue (the organization is in arrears), so the plan is suspended. | Settle the outstanding balance in Cobo Portal under **Bills & Payments** to restore service. For more information, see [Introduction to Bills & Payments](https://manuals.cobo.com/en/portal/bills-and-payments/introduction).                               |

#### Wallet configuration errors

| Error code | Description                                                                                                                                                                                                  | Solution                                                                                                                                                                                                                                                                                                                                                                  |
| ---------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 2101       | The wallet name exceeds the maximum allowed character length.                                                                                                                                                | Wallet names can contain up to 100 characters. The `error_message` reports the exact limit that applies to your request. Shorten the wallet name to that limit or fewer, then retry.                                                                                                                                                                                      |
| 2102       | The wallet name contains invalid characters.                                                                                                                                                                 | The Cobo API rejects wallet names that contain any of the following characters: `+`, `-`, `=`, `@`. Remove these characters from the wallet name and retry.                                                                                                                                                                                                               |
| 2103       | A wallet with this name already exists in the organization.                                                                                                                                                  | Wallet names must be unique within an organization. Choose a name that is not already used by another wallet and retry. To see names in use, list your existing wallets.                                                                                                                                                                                                  |
| 2104       | The specified chain is not enabled for this organization's pricing plan.                                                                                                                                     | To check which chains are already enabled, call the [List enabled chains](/developers/v2/api-references/wallets/list-enabled-chains) operation. If you need to enable or disable chains in Cobo Portal, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains). Then retry with a chain that is enabled for your organization.                  |
| 2105       | For UTXO-based tokens (such as BTC), all available UTXOs are currently locked by a pending transaction or a transaction pending KYT screening. A new transfer cannot proceed until those UTXOs are released. | Call the [List transactions](/developers/v2/api-references/transactions/list-transactions) operation, filtered to this wallet, to find the pending transactions that are holding the UTXOs. The UTXOs are released only when those transactions reach a terminal state (for example, completed or failed). Retry the transfer after the locking transactions reach a terminal state. |

#### Transfer errors

The following error codes are returned by transfer and withdrawal operations.

| Error code   | Description                                                                                                                                                                                                           | Solution                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| ------------ | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 30000        | Unauthorized. You do not have permission to perform this transfer.                                                                                                                                                    | Check the permissions and wallet scopes associated with your API key. See [Permissions and wallet scopes](/developers/v2/guides/overview/permissions-and-scopes) for details.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        |
| 30001, 12009 | The `request_id` has already been used.                                                                                                                                                                               | Use a unique `request_id` for each new transaction. Duplicate `request_id` values are rejected to prevent duplicate transactions.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| 30002        | The specified token is not supported for this operation or organization.                                                                                                                                              | Verify the `token_id` is correct. Call the [List supported tokens](/developers/v2/api-references/wallets/list-supported-tokens) operation to get the full list of supported tokens.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| 30003        | The wallet type does not support this transfer operation.                                                                                                                                                             | Verify that the wallet type is compatible with the requested transfer.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    |
| 30004        | The source wallet ID is invalid or the wallet does not exist.                                                                                                                                                         | Verify the `from_wallet_id` value is correct and the wallet belongs to your organization.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 |
| 30005        | The source address format is invalid or not compatible with the token.                                                                                                                                                | Provide a valid source address that is compatible with the token type.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    |
| 30006        | The source address encoding format is not supported.                                                                                                                                                                  | Use an address encoding format that is supported for this token.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                          |
| 30007        | Invalid amount. The value is not a valid number or does not meet the required format or range.                                                                                                                        | Provide a positive numeric amount. Call the [Get token information](/developers/v2/api-references/wallets/get-token-information) operation to retrieve the token's `decimal` precision and ensure the amount does not exceed it.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     |
| 30008        | The `abs_amount` value must be greater than 0.                                                                                                                                                                        | Provide a positive, non-zero value for `abs_amount`.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 30009        | The amount cannot be less than zero.                                                                                                                                                                                  | Provide a non-negative amount.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| 30010        | The withdrawal amount is below the minimum threshold for this token and cannot be processed.                                                                                                                          | Increase the withdrawal amount. Call the [Get token information](/developers/v2/api-references/wallets/get-token-information) operation to retrieve the `dust_threshold` value for this token.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       |
| 30011        | The deposit amount is below the minimum deposit threshold for this token.                                                                                                                                             | Increase the deposit amount. Call the [Get token information](/developers/v2/api-references/wallets/get-token-information) operation to retrieve the `minimum_deposit_threshold` value for this token.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                               |
| 30012, 12007 | The transfer amount exceeds the wallet's available balance.                                                                                                                                                           | Check the wallet's available balance, which equals the total balance minus any pending and reserved amounts. Call the [Get wallet balance](/developers/v2/api-references/wallets/get-wallet-balance) operation to verify.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| 30013        | The fee token balance is insufficient to cover the transaction fee.                                                                                                                                                   | Ensure the wallet or Fee Station has sufficient balance in the fee token (for example, ETH on EVM chains) to cover the transaction fee.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   |
| 30014        | The destination address is invalid or not compatible with the token.                                                                                                                                                  | Provide a valid destination address that is compatible with the token type.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                               |
| 30015        | The destination wallet ID is invalid or the wallet does not exist.                                                                                                                                                    | Verify the `to_wallet_id` value is correct and the wallet belongs to your organization.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   |
| 30016        | The number of transaction categories exceeds the maximum of 5.                                                                                                                                                        | Reduce the number of categories in the `category_names` field to 5 or fewer.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| 30017        | The category name exceeds the maximum of 30 characters.                                                                                                                                                               | Shorten the category name to 30 characters or fewer.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 30018        | The description exceeds the maximum of 100 characters.                                                                                                                                                                | Shorten the `description` field to 100 characters or fewer.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                               |
| 30022        | An invalid trading account type was specified as the transfer source for an Exchange Wallet.                                                                                                                          | Provide a valid trading account type as the transfer source.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| 30023        | An invalid trading account type was specified as the transfer destination for an Exchange Wallet.                                                                                                                     | Provide a valid trading account type as the transfer destination.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| 30024        | Neither `to_wallet_id` nor `to_address` was provided.                                                                                                                                                                 | Provide either `to_wallet_id` or `to_address` as the transfer destination.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                |
| 30025        | Withdrawals are currently unavailable for this wallet or token.                                                                                                                                                       | In Cobo Portal, open the target wallet, locate the target token in the wallet's token or asset list, and check whether that token row provides a **Withdraw** action. If **Withdraw** is not available, that wallet/token combination does not support withdrawals. If the token is not shown in the list, add the token to the wallet first; if the add-token flow indicates that the token's chain is not enabled, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains).                                                                                                                                                                                                                         |
| 30026        | Transfers are currently unavailable for this wallet.                                                                                                                                                                  | In Cobo Portal, open **Wallets** > the wallet type that matches this request > the target wallet, then verify from the wallet detail page that transfers are allowed for that wallet. If the wallet is restricted by wallet status, approval settings, or policy configuration, update the relevant setting before retrying.                                                                                                                                                                                                                                                                                                                                                                                                              |
| 30027        | Deposits into the destination wallet are currently unavailable.                                                                                                                                                       | Confirm that the destination token has been added to the destination wallet and that the token's chain is enabled for your organization. If you need to enable or disable chains in Cobo Portal, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains). If that token or wallet still does not support deposits, choose a destination wallet that supports deposits.                                                                                                                                                                                                                                                                                                                                |
| 30028        | The `request_id` parameter is missing or invalid.                                                                                                                                                                     | Provide a valid, non-empty `request_id` with the request.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 |
| 30029        | Trading account sub-wallets cannot initiate withdrawal transactions in an Exchange Wallet.                                                                                                                            | Use the Exchange Wallet's main account to initiate the withdrawal, not a trading account sub-wallet.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 30030        | The deposit or withdrawal operation cannot proceed because Cobo has temporarily suspended deposit or withdrawal processing for this token. The platform rejects the related operation until the suspension is lifted. | You cannot lift this suspension yourself; it is controlled on Cobo's side. To be notified when a token is suspended, subscribe to the `token.suspended.deposit` and `token.suspended.withdraw` events when you register a webhook endpoint, either on Cobo Portal (see [Register a webhook endpoint](https://manuals.cobo.com/en/portal/developer-console/webhooks-create), where you select the event types to subscribe to) or by calling the [Register webhook endpoint](/developers/v2/api-references/developers--webhooks/register-webhook-endpoint) operation (`POST /webhooks/endpoints`) with `subscribed_events` set to `["token.suspended.deposit", "token.suspended.withdraw"]`. Then retry the operation after the suspension is lifted. |
| 30031        | The specified token has not been enabled for this organization.                                                                                                                                                       | Call the [List enabled tokens](/developers/v2/api-references/wallets/list-enabled-tokens) operation to confirm the token is not yet enabled. Then add the token to the target wallet; if the flow indicates that the token's chain is not yet enabled, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains). Retry after the token is available in the wallet.                                                                                                                                                                                                                                                                                                                                                |
| 30032        | No key share holder group is available for signing in this MPC Wallet.                                                                                                                                                | In Cobo Portal, go to **Wallets** > **MPC Wallets** > the target vault > **Key Share Management**. Confirm that the vault has an available **Main Group** or **Signing Group** that can sign this transaction. If neither exists or the available group is unusable, create or recover the required group in **Key Share Management** first, then retry the transaction.                                                                                                                                                                                                                                                                                                                                                                  |
| 30033        | The recipient address does not belong to Cobo, or Cobo Loop has been disabled for these wallets.                                                                                                                      | Verify that the recipient address is a Cobo address and that Cobo Loop is enabled for both wallets. To send to a non-Cobo address, use a standard withdrawal instead.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     |
| 30035        | The Exchange Wallet is connected in Observation mode, which is read-only and does not support withdrawals.                                                                                                            | Switch to an Exchange Wallet connected in Normal mode, or use a different wallet that has withdrawal permissions.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| 30036        | The Fee Station balance is insufficient. Transactions cannot proceed until it is recharged.                                                                                                                           | In Cobo Portal, go to **Fee Station**. You can use the **USD / USD Stablecoins** tab to deposit supported USD stablecoins, or switch to the **Gas Token** tab to deposit the native gas token required by the target network. Retry after the balance is updated.                                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| 30037        | The source and destination wallets are not eligible for Cobo Loop transactions.                                                                                                                                       | Verify that both wallets support Cobo Loop. Use a standard transfer for wallets that are not Cobo Loop eligible.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                          |
| 30038        | The Fee Station token balance is insufficient to cover the transaction fee.                                                                                                                                           | In Cobo Portal, go to **Fee Station** > **Gas Token** and deposit the exact native gas token required by the network for this transaction. Retry after that token balance is sufficient.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| 30039        | Cobo's Fee Station balance is insufficient to pay for gas.                                                                                                                                                            | This error is caused by a temporary condition on Cobo's side. Retry after a short delay.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |

#### Token and balance errors

| Error code | Description                                                                      | Solution                                                                                                                                                                                                   |
| ---------- | -------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 12002      | The specified token is not supported by Cobo.                                    | Choose a supported token. Call the [List supported tokens](/developers/v2/api-references/wallets/list-supported-tokens) operation to get the full list of supported tokens.                                           |
| 12025      | The UTXOs specified in `included_utxos` or `excluded_utxos` are invalid.         | Verify the UTXOs specified in `included_utxos` or `excluded_utxos`.                                                                                                                                        |
| 60010      | The specified token has not been enabled for this organization.                  | Enable the token for your organization in Cobo Portal. Call the [List enabled tokens](/developers/v2/api-references/wallets/list-enabled-tokens) operation to see all tokens currently enabled for your organization. |
| 60020      | The specified address is not enabled for the given token and wallet combination. | Verify that the address is associated with the correct wallet and token in your organization settings.                                                                                                     |

#### Transaction management errors

| Error code | Description                                                                                   | Solution                                                                                                                                                                                                                                                                                                                 |
| ---------- | --------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 60001      | The specified organization was not found.                                                     | Verify that your API key belongs to the correct organization and that you are calling the correct environment.                                                                                                                                                                                                           |
| 60002      | The transaction type is invalid.                                                              | Provide one of the supported transaction types: `Transfer`, `ContractCall`, or `MessageSign`.                                                                                                                                                                                                                            |
| 60003      | The transaction fee could not be estimated.                                                   | Retry the fee estimation after a short delay. If the error persists, verify that the token is supported and that the chain is enabled for your organization. If you need to review or change enabled chains in Cobo Portal, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains). |
| 60004      | The transaction could not be found for the requested action.                                  | Verify the `transaction_id` value and confirm that the transaction exists in your organization.                                                                                                                                                                                                                          |
| 60005      | The transaction cannot be canceled because it is in a state that does not allow cancellation. | Check the current transaction status. Only transactions in certain states (such as `Pending`) can be canceled.                                                                                                                                                                                                           |
| 60006      | The transaction cannot be dropped.                                                            | The transaction is in a state that does not allow it to be dropped. Check the transaction status before retrying.                                                                                                                                                                                                        |
| 60007      | The transaction cannot be sped up.                                                            | The transaction is in a state that does not allow a speed-up. This may occur when the transaction is already confirmed or in a terminal state.                                                                                                                                                                           |

#### MPC wallet errors

| Error code | Description                                                          | Solution                                                                                                                                                                                                                                                                            |
| ---------- | -------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 50000      | The MPC Vault does not have backed-up key shares for the Main Group. | In Cobo Portal, go to **Wallets** > **MPC Wallets** > the target vault > **Key Share Management**. Open the **Main Group**, check its backup status, and complete the pending key share backup for every holder. Retry this operation only after the Main Group shows as backed up. |

#### Smart contract and EVM errors

The following error codes are returned by EVM contract call operations.

**Note:** Error codes 40001–40003 are also returned by transaction category operations with different meanings. Use the operation you called and the `error_message` to determine which meaning applies.

| Error code | Description                                                                      | Solution                                                                                                                                                                                                 |
| ---------- | -------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 5001       | The contract ABI is invalid or cannot be parsed.                                 | Verify that the ABI JSON is correctly formatted and complete.                                                                                                                                            |
| 5002       | One or more parameters passed to the EVM operation are invalid.                  | Check the parameter types and values against the contract ABI definition.                                                                                                                                |
| 5003       | The transaction calldata is invalid or improperly encoded.                       | Verify that the calldata is correctly ABI-encoded for the target function.                                                                                                                               |
| 5004       | The requested EVM resource was not found.                                        | Check the contract address and chain ID in the request.                                                                                                                                                  |
| 40001      | The external data source (such as a block explorer) rate limit has been reached. | Retry after a short delay. This is a temporary condition caused by upstream rate limits.                                                                                                                 |
| 40002      | The contract source code is not verified on the block explorer.                  | Verify the contract source code on the relevant block explorer (such as Etherscan) before attempting ABI-related operations.                                                                             |
| 40003      | The specified chain is not supported for this EVM operation.                     | Use a supported chain. If you need to review which chains are enabled for your organization in Cobo Portal, see [Enable or disable chains](https://manuals.cobo.com/en/portal/enable-or-disable-chains). |

#### MFA errors

The following error codes are returned when Cobo Guard multi-factor authentication (MFA) is required or fails.

| Error code | Description                                                                               | Solution                                                                                                                                                                                                                                                                                                                                                         |
| ---------- | ----------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 40201      | The Cobo Guard key provided is invalid or has expired.                                    | In Cobo Portal, click your avatar in the top-right corner, then go to **Account** > **Security**. In the **Cobo Guard** section, either click **View Pubkey and TSS Node ID** to confirm you are using the correct active key, or click **Reset** / **Set Up** to bind a new Cobo Guard key. After the active key is updated, retry the operation with that key. |
| 40202      | The Cobo Guard request is still pending and has not been completed.                       | Wait for the Guard request to be approved or rejected before proceeding.                                                                                                                                                                                                                                                                                         |
| 40203      | The Cobo Guard request has no approval or rejection result yet.                           | Check the status of the pending Guard request and complete it before retrying.                                                                                                                                                                                                                                                                                   |
| 40204      | The user performing this operation must be the same user who initiated the Guard request. | Ensure the same user account is used for both initiating and completing the Cobo Guard MFA request.                                                                                                                                                                                                                                                              |

#### Transaction category errors

The following error codes are returned by transaction category management operations.

**Note:** Error codes 40001–40003 are also returned by EVM operations with different meanings. Use the operation you called and the `error_message` to determine which meaning applies.

| Error code | Description                                                         | Solution                                             |
| ---------- | ------------------------------------------------------------------- | ---------------------------------------------------- |
| 40000      | The category name exceeds 30 characters.                            | Shorten the category name to 30 characters or fewer. |
| 40001      | The specified organization was not found.                           | Verify your organization ID and API key environment. |
| 40002      | The number of transaction categories has reached the maximum limit. | Delete unused categories before creating new ones.   |
| 40003      | A category with this name already exists in the organization.       | Use a unique category name.                          |
| 40004      | The category name contains invalid characters.                      | Use only allowed characters in the category name.    |

#### Compliance and KYT errors

The following error codes are returned by compliance and Know Your Transaction (KYT) operations.

| Error code | Description                                                                                                                                    | Solution                                                                                                                                                                                                                                                                                                                                                           |
| ---------- | ---------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 40101      | The compliance request for the specified `transaction_id` was not found.                                                                       | Verify the `transaction_id` is correct and that a compliance check has been initiated for it.                                                                                                                                                                                                                                                                      |
| 40102      | The compliance request cannot be retried because it is not in a failed state.                                                                  | Check the current status of the compliance request before retrying. Only requests in a `Failed` state can be retried.                                                                                                                                                                                                                                              |
| 40103      | This transaction does not support the requested operation (it is not an EOA/Web3 transaction, or it does not have an on-chain transaction ID). | Confirm that the request type you are submitting is supported by the compliance API.                                                                                                                                                                                                                                                                               |
| 40104      | The KYT disposal type provided is invalid.                                                                                                     | Provide a valid disposal type for the KYT operation.                                                                                                                                                                                                                                                                                                               |
| 40105      | The specified KYT request was not found.                                                                                                       | Verify the KYT request ID.                                                                                                                                                                                                                                                                                                                                         |
| 40106      | A disposal request for this KYT screening already exists.                                                                                      | Check for an existing disposal request before creating a new one.                                                                                                                                                                                                                                                                                                  |
| 40107      | A withdrawal request for this KYT disposal already exists.                                                                                     | Check for an existing withdrawal request before creating a new one.                                                                                                                                                                                                                                                                                                |
| 40108      | The `status` filter value provided when querying the KYT audit list is invalid.                                                                | Use a `status` value supported by that operation when querying the KYT audit list.                                                                                                                                                                                                                                                                                 |
| 40109      | No KYT screening request was found for the specified `transaction_id`.                                                                         | Verify the `transaction_id` and ensure that a KYT screening was initiated for it.                                                                                                                                                                                                                                                                                  |
| 40110      | No KYT screening request was found for the specified `screening_request_id`.                                                                   | Verify the `screening_request_id` value.                                                                                                                                                                                                                                                                                                                           |
| 40111      | The transaction's current status does not allow a disposal action.                                                                             | Check the transaction's current status before initiating a disposal.                                                                                                                                                                                                                                                                                               |
| 40112      | The disposal parameters provided are invalid for this transaction.                                                                             | Review the disposal parameters and ensure they are consistent with the transaction's screening result.                                                                                                                                                                                                                                                             |
| 40113      | The KYT request is already being disposed of or has already been disposed of, so a new disposal action cannot be initiated.                    | Do not submit a duplicate disposal request for the same KYT request. Confirm the request's current disposal status first, then decide whether any further action is needed.                                                                                                                                                                                        |
| 40114      | The transaction's current status does not allow an unfreeze action.                                                                            | Check the transaction's current status before attempting to unfreeze it.                                                                                                                                                                                                                                                                                           |
| 40115      | The disposal fee for the KYT request is invalid.                                                                                               | Provide both `estimated_fee_type` and `estimated_fee_detail` in the KYT disposal request. This error occurs when `estimated_fee_type` is empty, or when `estimated_fee_detail` is empty or cannot be parsed into a valid transaction fee object. Check the API reference for the disposal operation for the expected `estimated_fee_detail` structure, then retry. |
| 40116      | The disposal fee for the screening request is invalid.                                                                                         | Provide a non-empty `estimate_transaction_fee` value in the screening disposal request. This error occurs when that field is missing or empty.                                                                                                                                                                                                                     |
| 40117      | The fee payment method for the KYT disposal is invalid.                                                                                        | Set `fee_payment_method` to one of the allowed values: `CUSTOMER_FEE_STATION`, `CUSTOMER_CURRENT_ADDRESS`, or `COBO_FEE_STATION`. An empty or missing value is also rejected.                                                                                                                                                                                      |
| 40118      | The destination address for the KYT disposal is invalid.                                                                                       | The `to_address` must be either one of the original sender addresses of the screened transaction or a valid address on that transaction's chain. Provide an address that meets one of these conditions and retry.                                                                                                                                                  |
| 40119      | An error occurred during the KYT disposal process.                                                                                             | Verify your request parameters are correct, then retry. If the error persists, go to **Approvals** > **Initiated By Me** or **All Approvals** in Cobo Portal, open the KYT disposal approval record for this request, and review its latest status and failure details before resubmitting.                                                                        |
| 40120      | The disposal amount for the screening request is invalid.                                                                                      | Verify the disposal amount in the screening disposal request.                                                                                                                                                                                                                                                                                                      |
| 40121      | The disposal amount for the KYT request is invalid.                                                                                            | Verify the disposal amount in the KYT disposal request.                                                                                                                                                                                                                                                                                                            |
| 40122      | The wallet balance is insufficient to cover the estimated transaction fee for the disposal.                                                    | In Cobo Portal, open **Wallets** > the wallet type that holds the screened funds > the target wallet, and confirm that the wallet holds enough native gas token to pay the disposal fee. If your disposal uses Fee Station, also go to **Fee Station** and confirm the fee-paying token balance is sufficient there before retrying.                               |
| 40123      | A disposal action cannot be initiated because the transaction is not currently frozen.                                                         | A KYT disposal can only be applied to frozen transactions. Verify the transaction's current status before proceeding.                                                                                                                                                                                                                                              |
| 40124      | No compliance request was found for the specified transaction hash.                                                                            | Verify the transaction hash.                                                                                                                                                                                                                                                                                                                                       |
| 40125      | The app check request for the specified `transaction_id` was not found.                                                                        | Verify the `transaction_id` and ensure that a compliance app check was initiated for it.                                                                                                                                                                                                                                                                           |
| 40126      | The KYT screening completion result is invalid or malformed.                                                                                   | Review the result format returned by the KYT provider.                                                                                                                                                                                                                                                                                                             |

#### Travel Rule errors

The following error codes are returned by Travel Rule compliance operations.

| Error code | Description                                                                        | Solution                                                                                                        |
| ---------- | ---------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------- |
| 70001      | A general Travel Rule error occurred.                                              | Check the error message for details and review your Travel Rule request parameters.                             |
| 70002      | The originator KYC information is invalid or incomplete.                           | Provide complete and valid KYC information for the originator.                                                  |
| 70003      | The Travel Rule vendor code is invalid.                                            | Provide a valid vendor code.                                                                                    |
| 70004      | The originator's natural person entity information is missing or incomplete.       | Complete all required natural person entity fields for the originator.                                          |
| 70005      | The originator's legal entity information is missing or incomplete.                | Complete all required legal entity fields for the originator.                                                   |
| 70006      | The originator information is missing or incomplete.                               | Provide all required originator information.                                                                    |
| 70007      | An error occurred while entering the sender information.                           | Check the error message for details and verify the sender information fields.                                   |
| 70008      | This Travel Rule operation is not supported for self-custody wallets.              | Use a Cobo-managed wallet for this Travel Rule operation.                                                       |
| 70009      | Originator information has already been submitted for this record.                 | Originator information can only be submitted once per record. Review the existing record if updates are needed. |
| 70010      | The self-custody wallet signature verification failed.                             | Ensure the signature is generated correctly for the self-custody wallet address.                                |
| 70011      | The legal entity information is incomplete — required fields are missing.          | Provide all required fields for the legal entity.                                                               |
| 70012      | The natural person entity information is incomplete — required fields are missing. | Provide all required fields for the natural person entity.                                                      |
| 70013      | This address has already been verified.                                            | No further action is needed. Address verification is a one-time operation.                                      |

### HTTP status codes

| Status code | Description                                                                                                                          | Solution                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                           |
| ----------- | ------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 200         | OK.                                                                                                                                  | N/A                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                |
| 400         | Bad request.                                                                                                                         | Check the request parameters.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 401         | Unauthorized.                                                                                                                        | Check whether the API key matches the current environment (Dev/Prod), whether the API signature is correct, and whether the `timestamp` is valid and consistent with the fields used in signing.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   |
| 403         | Forbidden.                                                                                                                           | <ul><li>Check the business error code in the response body first (for example, `2025`/`4001`) and troubleshoot permissions, roles, scopes, and organization ownership accordingly.</li><li>If you access the API via a reverse proxy or gateway, check gateway policies, egress public IP, WAF/firewall rules, and whether headers or paths are blocked or rewritten (for example, Cloudflare or Nginx).</li><li>If the failure is permission-related, review the operator's role in **Organization Settings** > **User Roles** and review the API key's configuration in **Developers** > **Custody Developers** > **API Keys**.</li><li>If the operation is blocked by transaction governance, go to **Wallets** > **Transaction Policies** and confirm the relevant policy allows this API operation.</li></ul> |
| 404         | Not Found.                                                                                                                           | Check the requestURL.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| 405         | Method Not Allowed.                                                                                                                  | Use a supported HTTP method.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       |
| 406         | Not Acceptable.                                                                                                                      | Ensure the request content format is JSON.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| 429         | Too Many Requests.                                                                                                                   | Reduce request frequency and try again later.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| 500         | Internal Server Error. This error can be caused by several issues including expired [Org Access Tokens](/developers/v2/apps/org-access-tokens). | Check your server configuration settings, including whether your Org Access Token has expired, and try again later.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                |
| 502         | Bad Gateway.                                                                                                                         | Check the connectivity and try again later.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        |
| 503         | Service Unavailable.                                                                                                                 | Try again later.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   |


# Introduction to Wallet-as-a-Service (WaaS) 2.0
Source: https://cobo.com/developers/v2/guides/overview/introduction



<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

The Cobo Wallet-as-a-Service (WaaS) 2.0 API is the latest version of Cobo’s WaaS API offering. It enables you to access Cobo’s full suite of crypto wallet technologies with powerful and flexible access controls. By encapsulating complex security protocols and streamlining blockchain interactions, this API allows you to concentrate on your core business activities without worrying about the safety of your assets.

## Key features

The WaaS 2.0 API presents the following key features:

* A unified API for [all of Cobo’s wallet types](https://manuals.cobo.com/en/portal/introduction#an-all-in-one-wallet-platform)
* Support for 80+ chains and 3,000+ tokens
* A comprehensive selection of webhook events
* Flexible usage models for MPC wallets, including [Organization-Controlled Wallets](https://manuals.cobo.com/en/portal/mpc-wallets/ocw/introduction) and [User-Controlled Wallets](https://manuals.cobo.com/en/portal/mpc-wallets/ucw/introduction)
* Seamlessly transfer funds across multiple exchanges, including Binance, OKX, Bybit, Deribit, and more

## Cobo Portal

You can use the WaaS 2.0 API together with [Cobo Portal](https://manuals.cobo.com/en/portal/introduction), a web-based interface with the following features catering to developers' needs:

* [Developer Console](https://manuals.cobo.com/en/portal/developer-console/introduction), a central place for you to monitor API activities, oversee webhook events, view logs, and more.
* [Risk control mechanisms](https://manuals.cobo.com/en/portal/risk-controls/introduction), including customizable transaction policies, governance policies, and user roles and permissions.
* [Dashboard](https://manuals.cobo.com/en/portal/dashboard/introduction), which provides a comprehensive overview of your total asset value, asset allocations, transactions, and pricing plan usage.

## Use cases

With the WaaS 2.0 API, you can:

* **Enhance your own applications**: Whether you operate as an exchange, a payment service provider, a crypto-native firm, an OTC brokerage, or a retail platform, the WaaS 2.0 API empowers you to integrate Cobo’s powerful wallet capabilities directly into your applications. This integration enhances your applications’ functionality for managing digital assets, enabling you to better serve your users and stay ahead in the competitive market.
* **Build** [**Cobo Portal Apps**](https://manuals.cobo.com/en/portal/portal-apps/introduction): By leveraging the WaaS 2.0 API, you can also build apps to significantly expand the capabilities of Cobo Portal, providing valuable tools for staking, trading, and automating finance operations, and more.


# Permission list
Source: https://cobo.com/developers/v2/guides/overview/permission-list

Comprehensive list of resources and operations defining permissions for the WaaS 2.0 API.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This table lists the various resources and operations that collectively define permissions, and also the API operations that require these permissions.

<table>
  <thead>
    <tr>
      <th>Resources</th>
      <th>Operations</th>
      <th>Permission description</th>
      <th>Affected API operations</th>
    </tr>
  </thead>

  <tbody>
    <tr>
      <td>
        <div>organization\_profile</div>
      </td>

      <td>update</td>

      <td>
        <div>
          <div>Edit Organization Profile</div>
        </div>
      </td>

      <td>N/A</td>
    </tr>

    <tr>
      <td>freeze</td>

      <td>
        <div>
          <div>Freeze Organization</div>
        </div>
      </td>

      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>kyc\_profile</div>
      </td>

      <td>read</td>

      <td>
        <div>
          <div>View KYC Profile</div>
        </div>
      </td>

      <td>N/A</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit KYC Profile</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>team\_member</div>
      </td>

      <td>create</td>
      <td>Invite Members</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View Members</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Member User Roles</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>delete</td>
      <td>Delete Members</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>freeze</td>
      <td>Freeze Members</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>unfreeze</td>
      <td>Unfreeze Members</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>fee\_station</div>
      </td>

      <td>read</td>
      <td>View Fee Station</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Fee Station Settings</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>roles</div>
      </td>

      <td>read</td>
      <td>View Roles</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>create</td>
      <td>Create Customized User Roles</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Customized User Roles</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>activity\_logs</td>
      <td>read</td>
      <td>View Activities</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>app\_governance\_policy</div>
      </td>

      <td>update</td>
      <td>Edit APP Governance Policies</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View APP Governance Policies</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>governance\_policy</div>
      </td>

      <td>create</td>
      <td>Create Governance Policies</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View Governance Policies</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Governance Policies</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>delete</td>
      <td>Delete Governance Policies</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>transaction\_category</div>
      </td>

      <td>create</td>
      <td>Create Transaction Categories</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View Transaction Categories</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>bills</div>
      </td>

      <td>read</td>
      <td>View Bill Details</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>update\_billing\_emails</td>
      <td>Edit Billing Emails</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>pricing\_plan</div>
      </td>

      <td>read</td>
      <td>View Pricing Plan Details</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Pricing Plan</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>update\_supported\_chains</td>
      <td>Edit Supported Chains</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>wallet</div>
      </td>

      <td>create</td>
      <td>Create Wallets</td>
      <td>`POST /wallets`</td>
    </tr>

    <tr>
      <td>connect</td>
      <td>Cobo Connect</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>import</td>
      <td>Import Wallets</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View Wallets</td>
      <td>`GET /wallets`<br />`GET /wallets/{wallet_id}`<br />`GET /wallets/{wallet_id}/addresses`<br />`GET /wallets/{wallet_id}/addresses/{address}`<br />`GET /wallets/{wallet_id}/addresses/{address}/tokens`<br />`GET /wallets/{wallet_id}/tokens`<br />`GET /wallets/{wallet_id}/max_transferable_value`<br />`GET /wallets/{wallet_id}/exchanges/assets`<br />`GET /wallets/{wallet_id}/utxos`</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Wallets</td>
      <td>`PUT /wallets/{wallet_id}`</td>
    </tr>

    <tr>
      <td>delete</td>
      <td>Delete Wallets</td>
      <td>`POST /wallets/{wallet_id}/delete`</td>
    </tr>

    <tr>
      <td>create\_address</td>
      <td>Create Addresses</td>
      <td>`POST /wallets/{wallet_id}/addresses`</td>
    </tr>

    <tr>
      <td>manage\_utxo</td>
      <td>Manage UTXOs</td>
      <td>`POST /wallets/{wallet_id}/utxos/lock`<br />`POST /wallets/{wallet_id}/utxos/unlock`</td>
    </tr>

    <tr>
      <td>
        <div>transaction</div>
      </td>

      <td>read</td>
      <td>View Transactions</td>
      <td>`GET /transactions/{transaction_id}`</td>
    </tr>

    <tr>
      <td>export</td>
      <td>Export Transactions</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>withdraw</td>
      <td>Make Withdrawals</td>
      <td>`POST /transactions/transfer`</td>
    </tr>

    <tr>
      <td>estimate\_fee</td>
      <td>Estimate Transaction Fee</td>
      <td>`POST /transactions/check_loop_transfers`<br />`POST /transactions/estimate_fee`<br />`POST /stakings/estimate_fee`</td>
    </tr>

    <tr>
      <td>contract\_call</td>
      <td>Initiate Contract Calls</td>
      <td>`POST /transactions/contract_call`</td>
    </tr>

    <tr>
      <td>message\_sign</td>
      <td>Initiate Message Signings</td>
      <td>`POST /transactions/message_sign`</td>
    </tr>

    <tr>
      <td>stake</td>
      <td>Stake Assets</td>
      <td>`POST /stakings/activities/stake`</td>
    </tr>

    <tr>
      <td>manage</td>
      <td>Manage Ongoing Transactions</td>
      <td>`POST /transactions/{transaction_id}/resend`<br />`POST /transactions/{transaction_id}/cancel`<br />`POST /transactions/{transaction_id}/drop`<br />`POST /transactions/{transaction_id}/speedup`</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Transaction Notes</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>unstake</td>
      <td>Unstake Assets</td>
      <td>`POST /stakings/activities/unstake`</td>
    </tr>

    <tr>
      <td>unstake\_withdraw</td>
      <td>Withdraw Unstaked Assets</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>travel\_rule</div>
      </td>

      <td>read</td>
      <td><div>View Travel Rule</div></td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>edit</td>
      <td><div>Edit Travel Rule</div></td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>mpc\_project</div>
      </td>

      <td>create</td>
      <td>Create Projects</td>
      <td>`POST /wallets/mpc/projects`</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View Projects</td>
      <td>`GET /wallets/mpc/projects`<br />`GET /wallets/mpc/projects/{project_id}`</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Projects of MPC Wallets</td>
      <td>`PUT /wallets/mpc/projects/{project_id}`</td>
    </tr>

    <tr>
      <td>
        <div>mpc\_vault</div>
      </td>

      <td>create</td>
      <td>Create Vaults for MPC Wallets</td>
      <td>`POST /wallets/mpc/vaults`</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View Vaults</td>
      <td>`GET /wallets/mpc/vaults`<br />`GET /wallets/mpc/vaults/{vault_id}`</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Vaults of MPC Wallets</td>
      <td>`PUT /wallets/mpc/vaults/{vault_id}`</td>
    </tr>

    <tr>
      <td>
        <div>mpc\_key\_group</div>
      </td>

      <td>create</td>
      <td>Create Key Share Holder Groups</td>
      <td>`POST /wallets/mpc/vaults/{vault_id}/key_share_holder_groups`<br />`POST /wallets/mpc/vaults/{vault_id}/tss_requests`</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View Key Share Holder Groups</td>
      <td>`GET /wallets/mpc/vaults/{vault_id}/key_share_holder_groups`<br />`GET /wallets/mpc/vaults/{vault_id}/key_share_holder_groups/{key_share_holder_group_id}`<br />`GET /wallets/mpc/vaults/{vault_id}/tss_requests`<br />`GET /wallets/mpc/vaults/{vault_id}/tss_requests/{tss_request_id}`</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Key Share Holder Groups</td>
      <td>`PUT /wallets/mpc/vaults/{vault_id}/key_share_holder_groups/{key_share_holder_group_id}`<br />`PUT /wallets/mpc/vaults/{vault_id}/tss_requests/{tss_request_id}`</td>
    </tr>

    <tr>
      <td>delete</td>
      <td>Delete Key Share Holder Groups</td>
      <td>`POST /wallets/mpc/vaults/{vault_id}/key_share_holder_groups/{key_share_holder_group_id}/delete`<br />`POST /wallets/mpc/vaults/{vault_id}/tss_requests/{tss_request_id}/cancel`</td>
    </tr>

    <tr>
      <td>
        <div>address\_book</div>
      </td>

      <td>create</td>
      <td>Add Addresses to Address Books</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View Addresses in Address Books</td>
      <td>`GET /address_books`</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Addresses in Address Books</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>delete</td>
      <td>Delete Addresses From Address Books</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>transaction\_policy</div>
      </td>

      <td>create</td>
      <td>Create Transaction Policies</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View Transaction Policies</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>update</td>
      <td>Edit Transaction Policies</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>delete</td>
      <td>Delete Transaction Policies</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>api\_key</div>
      </td>

      <td>edit</td>
      <td>Edit API Keys</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View API Keys</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>api\_log</div>
      </td>

      <td>read</td>
      <td>View API Logs</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>export</td>
      <td>Export API Logs</td>
      <td>N/A</td>
    </tr>

    <tr>
      <td>developer\_dashboard</td>
      <td>view</td>

      <td>
        <div>
          <div>View Developer Console Dashboard</div>
        </div>
      </td>

      <td>N/A</td>
    </tr>

    <tr>
      <td>
        <div>webhook</div>
      </td>

      <td>edit</td>
      <td>Edit Webhook URLs</td>
      <td>`POST /webhooks/endpoints`<br />`POST /webhooks/endpoints/{endpoint_id}`</td>
    </tr>

    <tr>
      <td>read</td>
      <td>View Webhook URLs/Events</td>
      <td>`GET /webhooks/endpoints`<br />`GET /webhooks/endpoints/{endpoint_id}`<br />`GET /webhooks/endpoints/{endpoint_id}/events`<br />`GET /webhooks/endpoints/{endpoint_id}/events/{event_id}`<br />`GET /webhooks/endpoints/{endpoint_id}/events/{event_id}/logs`</td>
    </tr>

    <tr>
      <td>resend</td>
      <td>Resend Webhook Events</td>
      <td>`POST /webhooks/endpoints/{endpoint_id}/events/{event_id}/retry`</td>
    </tr>

    <tr>
      <td>
        <div>callback</div>
      </td>

      <td>edit</td>

      <td>
        <div>
          <div>Edit Callback URLs</div>
        </div>
      </td>

      <td>N/A</td>
    </tr>

    <tr>
      <td>read</td>

      <td>
        <div>
          <div>View Callback URLs/Messages</div>
        </div>
      </td>

      <td>N/A</td>
    </tr>

    <tr>
      <td>resend</td>

      <td>
        <div>
          <div>Resend Callback Messages</div>
        </div>
      </td>

      <td>N/A</td>
    </tr>
  </tbody>
</table>


# Permissions and wallet scopes
Source: https://cobo.com/developers/v2/guides/overview/permissions-and-scopes

Detailed explanation of permissions and wallet scopes in WaaS 2.0 for secure access control.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

In WaaS 2.0, permissions and wallet scopes are a crucial part of maintaining robust security and precise access control. They ensure that users, whether developers or end-users, are granted the appropriate level of access to resources and operations. This access control applies universally across all user categories:

* General developers: API operations require specific permissions.
* Cobo Portal Apps developers: Applications are restricted to accessing only the resources within their authorized scopes.
* Cobo Portal users: Permissions control access to resources, operations, and transactions within Cobo Portal.

This permissions framework is designed to provide a seamless and secure user experience, aligning with organizational policies and compliance requirements.

## Key concepts

### Permissions

A permission is a specific combination of a resource and an operation, defining what actions a user can perform on a given resource. For example, `transaction:withdraw` indicates that the resource `transaction` paired with the operation `withdraw` grants permission to initiate withdrawal transactions. Permissions govern functional access, specifying which actions users are authorized to perform, while data boundaries are controlled through wallet scopes.

### Wallet scopes

A wallet scope defines the boundaries within which wallet-related permissions are effective, specifying access at levels such as wallet type, wallet ID, and other identifiers. Each type of wallet scope limits permissions to a specific subset of resources, ensuring a tailored access model. The wallet scope dimensions include:

* Wallet type
* Wallet sub-type
* Project ID (for MPC Wallets only)
* Vault ID (for MPC Wallets only)
* Wallet ID

### User roles

A user role is a collection of permissions that defines what resources and actions are available to users. Each role grants a specific set of permissions that determine users' capabilities, such as viewing, operating, or managing resources. For more information, refer to [Introduction to user roles and permissions](https://manuals.cobo.com/en/portal/organization/roles-and-permissions).

## Assign and manage permissions

### General developers via API key

For general developers, permissions and wallet scope are associated with the API key. When you register an API key, you select user roles and define the wallet scope, which grants shared permissions to all developers using that key. For more details, refer to [API key](/developers/v2/guides/overview/cobo-auth#api-key) and [Register an API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key).

<Note>
  Editing an API key's roles or wallet scope in Cobo Portal requires **Admin approval in Cobo Guard** before the change takes effect. Until an Admin approves the pending request, the previous (narrower) permissions remain active. If you have updated permissions but still receive HTTP 403 / error code 2025 or 4001, check whether the Cobo Guard approval has been completed.
</Note>

### Cobo Portal Apps developers via Org Access Tokens

Permissions for Cobo Portal Apps to access users' organization resources are granted through an Org Access Token. When a user installs an app, the necessary permissions and wallet scope are set, and once approved by the organization's admin, these are linked to the app's Org Access Token. Therefore, before publishing an app, developers should specify both required and optional permissions in the [app's manifest file](/developers/v2/apps/build-app#configure-the-manifest-file) to ensure proper access is granted. For a comprehensive list of permissions, refer to [Permissions list](/developers/v2/guides/overview/permission-list).

### Cobo Portal users via user roles

Permissions for Cobo Portal users are based on their user role and wallet scope, with predefined roles available and customizable options for specific needs. For more details, refer to [Assign user roles to members](https://manuals.cobo.com/en/portal/organization/assign-roles-to-members).


# Upgrade from WaaS 1.0 to 2.0
Source: https://cobo.com/developers/v2/guides/overview/upgrade-guide

Guide for upgrading from WaaS 1.0 to 2.0, highlighting benefits and providing step-by-step instructions.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This article is targeted at WaaS 1.0 users who are considering upgrading to WaaS 2.0. It introduces the benefits of the upgrade and provides step-by-step instructions to successfully complete the upgrade process.

## Key enhancements in WaaS 2.0

WaaS 2.0 is a major upgrade from WaaS 1.0, designed to support diverse Web3 scenarios such as payments, tokenization, and automated fund management. It enables enterprises and developers to build Web3 applications more efficiently and cost-effectively.

The three core benefits of upgrading to WaaS 2.0 are:

* **Enhanced capabilities**: Introduces new modules including Payment Solutions, Tokenization, Fee Station, Auto-sweep, Travel Rule, and more.
* **More efficient development**: A unified API architecture reduces the number of API calls required to accomplish the same functionality, lowering integration and maintenance complexity.
* **Improved operations**: Upgraded webhook functionality supports more event types and provides built-in tools such as logs, retries, and simulated testing, enhancing observability and debugging efficiency.

For a complete introduction to WaaS 2.0, see [Introduction to WaaS 2.0](/developers/v2/guides/overview/introduction).

The following table summarizes the key enhancements introduced in WaaS 2.0 compared with WaaS 1.0:

| Dimension               | WaaS 1.0                                                                                                                                                                                                                                                                                                                                                                                       | WaaS 2.0                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| ----------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| **API Architecture**    | **Wallet-type-based structure**: The same business functionality required different API operations depending on wallet type. For example: <ul><li>Withdrawals for Custodial Wallets and MPC Wallets required separate API operations.</li><li>Querying a transaction by different IDs (such as transaction hash, transaction ID, internal ID) also required separate API operations.</li></ul> | **Scenario-driven structure**: The same business functionality can now be completed with a single API operation. For example: <ul><li>The [token transfer](/developers/v2/api-references/transactions/transfer-token) operation can handle deposits and withdrawals for all wallet types.</li><li>[Transaction queries](/developers/v2/api-references/transactions/list-all-transactions) are unified under a single API operation and support any type of ID.</li></ul>                                                                                                                                                                                                                                                                                                                  |
| **New Feature Modules** | N/A                                                                                                                                                                                                                                                                                                                                                                                            | <ul><li>[Payment](/developers/v2/payments/overview): A complete cryptocurrency payment solution.</li><li>[Tokenization](/developers/v2/api-references/tokenization/issue-token): Issue and manage tokenized on-chain assets.</li><li>[Fee Station](/developers/v2/api-references/feestation/get-fee-station-transaction-information): Handle gas fees and manage unified cost settlements.</li><li>[Auto-sweep](/developers/v2/api-references/autosweep/create-auto-sweep-task): Automatically consolidate token balances.</li><li>[Travel Rule](/developers/v2/api-references/travelrule/submit-travel-rule-information-for-deposits): Meet more comprehensive regulatory compliance requirements.</li><li>[Cobo Portal Apps](/developers/v2/apps/introduction): Develop and manage apps within the Cobo Portal ecosystem.</li></ul> |
| **Webhook Mechanism**   | Only supported transaction status notifications.                                                                                                                                                                                                                                                                                                                                               | <ul><li>**Support for more [event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type)**: Includes transaction, wallet, address, balance, and TSS-related events.</li><li>**Built-in [debugging tools](/developers/v2/api-references/developers--webhooks/trigger-test-event)**: Provides logs, automatic retries, and simulated event testing.</li></ul>                                                                                                                                                                                                                                                                                                                                                                                                                  |
| **Developer Tools**     | Provided basic SDKs.                                                                                                                                                                                                                                                                                                                                                                           | Expands the developer ecosystem with additional tools: <ul><li>[Cobo CLI](/developers/v2/developer-tools/cobo-cli): A command-line tool for rapid testing and debugging.</li><li>[UI Toolkit](/developers/v2/developer-tools/uitoolkit-intro): Pre-built UI components to accelerate app development.</li></ul>                                                                                                                                                                                                                                                                                                                                                                                                                                                                           |

## Technical changes and migration reference

This section is intended for developers. It explains the key technical changes between WaaS 1.0 and WaaS 2.0 in areas such as API design, authentication, and callback mechanisms, and provides a comparison table of common API operations to help you migrate quickly.

### Technical changes

The following table summarizes the key technical changes between WaaS 1.0 and WaaS 2.0, including API design, authentication, and callback mechanisms.

|                            | WaaS 1.0                                                                                                                                                                                                                                                                                                                | WaaS 2.0                                                                                                                                                                                                                                                                                                                                             |
| -------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| API design                 | HTTP endpoints supporting the GET and POST methods.                                                                                                                                                                                                                                                                     | RESTful API structured into distinct domains, such as wallets, transactions, and webhooks. The API follows resource-oriented design principles for endpoint definition and supports standard HTTP methods including GET, POST, PUT, and DELETE.                                                                                                      |
| API key and authentication | <ul><li>The API key is wallet-specific, meaning it can only be used to access the associated wallet.</li><li>An SECP256k1 signature is used for authenticating an API request.</li></ul>                                                                                                                                | <ul><li>The API key is organization-specific and can be used to access multiple wallets. For more information, refer to [Register an API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key).</li><li>An ED25519 signature is used for authenticating an API request.</li></ul>                                                |
| Transaction notification   | Supports transaction status-related events only.                                                                                                                                                                                                                                                                        | <ul><li>This feature is called “Webhook” in 2.0.</li><li>Supports [transaction status and TSS request-related events](/developers/v2/guides/webhooks-callbacks/webhook-event-type), and the list is still growing.</li><li>The data structure of the webhook event differs from 1.0.</li></ul>                                                                  |
| Withdrawal confirmation    | A mechanism used for confirming withdrawals initiated through WaaS API.                                                                                                                                                                                                                                                 | <ul><li>This feature is called “Callback” in 2.0.</li><li>The data structure of the callback message differs from 1.0.</li></ul>                                                                                                                                                                                                                     |
| Supported wallet types     | <ul><li>Custodial Wallets</li><li>MPC Wallets </li></ul>                                                                                                                                                                                                                                                                | <ul><li>[Custodial Wallets](https://manuals.cobo.com/en/portal/custodial-wallets/introduction)</li><li>[MPC Wallets](https://manuals.cobo.com/en/portal/mpc-wallets/introduction)</li><li>[Exchange Wallets](https://manuals.cobo.com/en/portal/exchange-wallets/introduction) </li></ul>                                                            |
| Asset model                | <ul><li>A coin is considered a unique asset type.</li><li>A coin represents a specific pairing of a chain and a cryptocurrency, such as ETH\_USDT.</li></ul>                                                                                                                                                            | <ul><li>A token is considered a unique asset type, except for Exchange Wallets, which consider an “asset” to be a unique asset type. </li><li>A token represents a specific pairing of a chain and a cryptocurrency, such as ETH\_USDT.</li><li>An asset represents a cryptocurrency stored in your linked exchange account, such as USDT.</li></ul> |
| Balance model              | <ul><li>**\[Custodial Wallets]** Coin balances can be calculated for an entire wallet but not for each address.</li><li>**\[MPC Wallets]** Coin balances can be calculated for each address within the wallet, but not for an entire wallet.</li></ul>                                                                  | <ul><li>**\[Custodial Wallets]** Token balances can be calculated for the entire wallet but not for each address.</li><li>**\[MPC Wallets]** Token balances can be calculated for the entire wallet or each address.</li></ul>                                                                                                                       |
| Balances and amounts       | <ul><li>Balances and amounts are denominated in the smallest units of the cryptocurrency. For example, Bitcoin balances and amounts are denominated in Satoshis.</li><li>The parameters `abs_balance` and `abs_amount` are denominated in the primary unit of the cryptocurrency, such as BTC for Bitcoin. </li></ul>   | <ul><li>Balances and amounts are denominated in the primary unit of the cryptocurrency, such as BTC for Bitcoin.</li><li>As an example, for a deposit of 1.2 BTC, the deposit amount is recorded as `120,000,000` in 1.0 and `1.2` in 2.0. </li></ul>                                                                                                |
| Address generation         | <ul><li>**\[Custodial Wallets]** Addresses are generated based on a specified coin, such as ETH\_USDT, and can then be used by all coins on the same chain.</li><li>**\[MPC Wallets]** Addresses are generated based on a specified chain, such as ETH, and can then be used by all coins on the same chain. </li></ul> | **\[Custodial Wallets / MPC Wallets]** Addresses are generated based on a specified chain, such as ETH, and can then be used by all tokens on the same chain.                                                                                                                                                                                        |
| Transaction ID             | The unique ID of a transaction.                                                                                                                                                                                                                                                                                         | <ul><li>The transaction ID in 2.0 follows the UUID format which differs from the format used in 1.0.</li><li>The transaction ID in 1.0 is termed as “Cobo ID” in 2.0. You can continue to use Cobo ID to query a transaction.</li></ul>                                                                                                              |

### API operation comparison

The following table lists the API operations needed for common wallet operations in WaaS 1.0 and 2.0 respectively. You can refer to this table when migrating your code from 1.0 to 2.0.

|                            | WaaS 1.0                                                                                                                                                                                                                                                                                                        | WaaS 2.0                                                                                                                                                                                            |
| -------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| Create a wallet            | Not supported since the API key is wallet-specific                                                                                                                                                                                                                                                              | [Create wallet](/developers/v2/api-references/wallets/create-wallet)                                                                                                                                           |
| Create an address          | <ul><li>**\[Custodial Wallets]** [Get New Deposit Address](/developers/v1/api-references/custody-wallet/new_address)</li><li>**\[MPC Wallets]** [Generate Addresses](/developers/v1/api-references/mpc-wallet/mpc_generate_addresses) and [Generate Address Memos](/developers/v1/api-references/mpc-wallet/mpc_generate_address_memo)</li></ul> | [Create addresses in wallet](/developers/v2/api-references/wallets/create-addresses-in-wallet)                                                                                                                 |
| Withdraw tokens            | <ul><li>**\[Custodial Wallets]** [New withdraw request](/developers/v1/api-references/custody-wallet/new_withdraw_request)</li><li>**\[MPC Wallets]** [Create Transaction](/developers/v1/api-references/mpc-wallet/mpc_create_transaction)</li></ul>                                                                                 | [Transfer token](/developers/v2/api-references/transactions/transfer-token)                                                                                                                                    |
| RBF transaction (Speed up) | **\[MPC Wallets]** [Speedup Transaction](/developers/v1/api-references/mpc-wallet/mpc_speedup_transaction)                                                                                                                                                                                                                 | [Speed up transaction](/developers/v2/api-references/transactions/speed-up-transaction)                                                                                                                        |
| RBF transaction (Drop)     | **\[MPC Wallets]** [Drop Transaction](/developers/v1/api-references/mpc-wallet/mpc_drop_transaction)                                                                                                                                                                                                                       | [Drop transaction](/developers/v2/api-references/transactions/drop-transaction)                                                                                                                                |
| Cancel transaction         | Not supported                                                                                                                                                                                                                                                                                                   | [Cancel transaction](/developers/v2/api-references/transactions/cancel-transaction)                                                                                                                            |
| Call a contract            | Not supported                                                                                                                                                                                                                                                                                                   | [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract)                                                                                                                          |
| Sign a message             | Not supported                                                                                                                                                                                                                                                                                                   | [Sign message](/developers/v2/api-references/transactions/sign-message)                                                                                                                                        |
| Query a transaction        | <ul><li>**\[Custodial Wallets]** [Transaction history](/developers/v1/api-references/custody-wallet/transaction_history)</li><li>**\[MPC Wallets]** [Get Transactions List](/developers/v1/api-references/mpc-wallet/mpc_list_transactions)</li></ul>                                                                                 | <ul><li>[List all transactions](/developers/v2/api-references/transactions/list-all-transactions)</li><li>[Get transaction information](/developers/v2/api-references/transactions/get-transaction-information)</li></ul> |

<Warning>
  WaaS 2.0 list endpoints, such as [List all transactions](/developers/v2/api-references/transactions/list-all-transactions), return results in pages. By default each page returns 10 records, and the maximum page size is 50, set with the `limit` parameter. This differs from WaaS 1.0, where a single response could return all results. A single WaaS 2.0 page therefore omits later results. To retrieve every record, iterate through all pages using the cursor parameters `before` and `after`.
</Warning>

## Upgrade to 2.0

This section introduces the detailed steps to upgrade from WaaS 1.0 to 2.0.

### Prerequisites

Reach out to our support team at [help@cobo.com](mailto:help@cobo.com) to migrate from Cobo Custody to Cobo Portal.

### Get started with WaaS 2.0

Follow the instructions in [Send your first request](/developers/v2/guides/get-started/get-started-with-waas) to set up your account, create and register your API key, integrate a WaaS SDK if necessary, and send your first API request to the WaaS 2.0 service.

### Rewrite your code

Once you complete the initial setup, it is time to rewrite your code by replacing the 1.0 API operations with 2.0 operations. Refer to[ API operation comparison](#api-operation-comparison) for a detailed comparison between 1.0 and 2.0 API operations.

You can also refer to [Get started with Custodial Wallets (Asset Wallets)](/developers/v2/guides/custodial-wallets/get-started-asset-wallets) for a step-by-step guide on how to create a Custodial Wallet (Asset Wallet), generate wallet addresses, and receive and withdraw tokens. Guides for other wallet types will be available in the future.

### Set up webhook and callback endpoints

Set up the webhook and callback endpoints and register them in Cobo Portal.

To understand webhook events, callback messages, and the differences in webhook/callback mechanisms between WaaS 1.0 and WaaS 2.0, refer to [Introduction to webhooks and callbacks](/developers/v2/guides/webhooks-callbacks/introduction).

To learn the detailed steps of the setup, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint). To register the endpoint, see [Register a webhook endpoint](https://manuals.cobo.com/en/portal/developer-console/webhooks-create) and [Register a callback endpoint](https://manuals.cobo.com/en/portal/developer-console/callbacks-register).

<Note>The endpoints you set up for WaaS 1.0 will not receive any messages from the WaaS 2.0 service.</Note>


# Batch transfers using smart contracts
Source: https://cobo.com/developers/v2/guides/transactions/batch-transfer

Use the WaaS 2.0 API to call a batch transfer smart contract and complete multiple token transfers in a single transaction.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

A batch transfer smart contract allows you to execute multiple token transfers in a single on-chain transaction, making it suitable for scenarios such as batch payouts or batch withdrawals. Compared to repeatedly calling the transfer API, the batch method reduces the need for multiple signatures and requests, improving operational efficiency.

This guide explains how to use the [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract) API to invoke the batch transfer smart contract deployed by Cobo, enabling batch token transfers.

<Note>The transaction fee for batch transfers using the smart contract API may not necessarily be lower than the total fee for multiple individual transfer token API calls. The actual cost depends on the on-chain gas price and the number of transfers; with a small number of recipients, batch transfers could even be more expensive. We recommend using the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) API to compare the cost of both approaches before initiating a transfer.</Note>

## Supported chains

The following EVM-compatible chains are supported:

* Ethereum Mainnet
* BNB Smart Chain
* Base Mainnet
* Arbitrum One
* Polygon PoS

The address of the batch transfer smart contract is [`0x3d963e23a9229D2ACd25E9FFC358be1a35460ecc`](https://etherscan.io/address/0x3d963e23a9229D2ACd25E9FFC358be1a35460ecc#code)

## Prerequisites

* You have set up Cobo Accounts and successfully sent requests as described in [Send your first API request](/developers/v2/get-started/get-started-with-waas).
* You are familiar with and able to use the [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract) API.
* You have basic knowledge of interacting with smart contracts, including preparing `calldata`, locating contract methods, and using the `approve` method on a token contract to authorize the batch transfer contract to spend tokens.
* The batch transfer feature currently only supports transactions initiated from MPC Wallets and Custodial Wallets (Web3 Wallets).

## Batch transfer of ETH

The following steps apply to batch transfers of ETH (native coin) on the supported chains:

1. **Prepare parameters**
   * Use the `sendEther` method to generate `calldata` (either with Cobo’s [script](#example-script-for-generating-calldata) or your own tool).\
     When generating `calldata`, provide:
     * `recipients (address[])`: array of recipient addresses.
     * `values (uint256[])`: array of amounts for each address (in wei).
   * The number of recipients must not exceed 200 (`recipients` array length ≤ 200).

2. **Call the [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract) API**
   * Specify the batch transfer contract address: [`0x3d963e23a9229D2ACd25E9FFC358be1a35460ecc`](https://etherscan.io/address/0x3d963e23a9229D2ACd25E9FFC358be1a35460ecc#code)
   * Provide the generated `calldata`.
   * The `value` in the API request must equal the sum of all values in the `values` array in the `calldata`.

3. **Wait for confirmation and check results**
   * Use the returned `tx_hash` to check the transaction status.
   * In Cobo Portal’s transaction history, you will see a transaction of the contract call type.
   * If any recipient address belongs to a Cobo Account, the corresponding organization will also see a transaction of the deposit type.

## Batch transfer of other tokens

The following steps apply to batch transfers of ERC-20 tokens on the supported chains:

1. **Call the token contract’s `approve` method**
   * Each token has its own contract address, so run `approve` on the specific token’s contract.
   * Approve the **source address** (the one specified in the `source` field of the smart contract call request).
   * The approved amount must be greater than or equal to the total transfer amount.
     <Note>Before calling the batch transfer contract, use an on-chain query or API request to confirm that the `approve` transaction has been successfully confirmed and completed.</Note>

2. **Prepare parameters**
   * Use the `sendToken` method to generate `calldata` (either with Cobo’s [script](#example-script-for-generating-calldata) or your own tool).\
     When generating `calldata`, provide:
     * `token (address)`: ERC-20 token contract address.
     * `recipients (address[])`: array of recipient addresses.
     * `values (uint256[])`: array of amounts for each address (in the token’s smallest unit).
   * The number of recipients must not exceed 200 (`recipients` array length ≤ 200).

3. **Call the [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract) API**
   * Specify the batch transfer contract address: [`0x3d963e23a9229D2ACd25E9FFC358be1a35460ecc`](https://etherscan.io/address/0x3d963e23a9229D2ACd25E9FFC358be1a35460ecc#code)
   * Provide the generated `calldata`.
   * Set `value` to 0 when making the API call.

4. **Wait for confirmation and check results**
   * Use the returned `tx_hash` to check the transaction status.
   * In Cobo Portal’s transaction history, you will see a transaction of the contract call type.
   * If any recipient address belongs to a Cobo Account, the corresponding organization will also see a transaction of the deposit type.

## Additional notes

* You can use [Fee Station](https://manuals.cobo.com/cn/portal/fee-station/introduction) to pay on-chain transaction fees with gas tokens or USD stablecoins.
* You can also manually call the batch transfer smart contract with the “Write Contract” function on a blockchain explorer. This method requires connecting your MPC Wallet or Custodial Wallet (Web3 Wallet) using a supported browser extension (such as [Cobo Connect](https://manuals.cobo.com/cn/cobo-connect/introduction)), without using API calls.

## Common failure causes

* Insufficient balance or insufficient approval amount.
* Mismatch between the length of `recipients` and the length of the amount array.
* Number of recipients exceeds the limit.
* Mismatch between the `value` in the API request and the amounts in the `calldata` (for ETH transfers).
* Insufficient gas limit.

## Example script for generating `calldata`

The following is a Python script provided by Cobo to generate `calldata`. You can also generate on your own.

```python expandable theme={null}
# !/usr/bin/env python3
"""
Contract Call Data Generator

This script generates call data for the provided smart contract ABI.
It supports all functions defined in the ABI including multicall, send, sendEther, sendToken, etc.
"""

import json
from web3 import Web3
from typing import List, Optional, Union
from eth_utils import to_checksum_address


class ContractCallDataGenerator:
    def __init__(self, abi_json: str):
        """
        Initialize the generator with contract ABI

        Args:
            abi_json (str): JSON string of the contract ABI
        """
        self.abi = json.loads(abi_json)
        self.w3 = Web3()
        self.contract = self.w3.eth.contract(abi=self.abi)

    def get_eth_address_calldata(self) -> str:
        """Generate calldata for ETH_ADDRESS() function"""
        return self.contract.encodeABI(fn_name='ETH_ADDRESS')

    def get_owner_calldata(self) -> str:
        """Generate calldata for owner() function"""
        return self.contract.encodeABI(fn_name='owner')

    def get_renounce_ownership_calldata(self) -> str:
        """Generate calldata for renounceOwnership() function"""
        return self.contract.encodeABI(fn_name='renounceOwnership')

    def get_transfer_ownership_calldata(self, new_owner: str) -> str:
        """
        Generate calldata for transferOwnership(address newOwner) function

        Args:
            new_owner (str): New owner address
        """
        new_owner = to_checksum_address(new_owner)
        return self.contract.encodeABI(
            fn_name='transferOwnership',
            args=[new_owner]
        )

    def get_rescue_calldata(self, token: str, amount: int) -> str:
        """
        Generate calldata for rescue(address _token, uint256 _amount) function

        Args:
            token (str): Token contract address
            amount (int): Amount to rescue
        """
        token = to_checksum_address(token)
        return self.contract.encodeABI(
            fn_name='rescue',
            args=[token, amount]
        )

    def get_multicall_calldata(self, data: List[bytes]) -> str:
        """
        Generate calldata for multicall(bytes[] data) function

        Args:
            data (List[bytes]): List of encoded function calls
        """
        return self.contract.encodeABI(
            fn_name='multicall',
            args=[data]
        )

    def get_send_ether_calldata(self, recipients: List[str], values: List[int]) -> str:
        """
        Generate calldata for sendEther(address[] recipients, uint256[] values) function

        Args:
            recipients (List[str]): List of recipient addresses
            values (List[int]): List of values to send
        """
        recipients = [to_checksum_address(addr) for addr in recipients]
        return self.contract.encodeABI(
            fn_name='sendEther',
            args=[recipients, values]
        )

    def get_send_token_calldata(self, token: str, recipients: List[str], values: List[int]) -> str:
        """
        Generate calldata for sendToken(contract IERC20 token, address[] recipients, uint256[] values) function

        Args:
            token (str): Token contract address
            recipients (List[str]): List of recipient addresses
            values (List[int]): List of values to send
        """
        token = to_checksum_address(token)
        recipients = [to_checksum_address(addr) for addr in recipients]
        return self.contract.encodeABI(
            fn_name='sendToken',
            args=[token, recipients, values]
        )

    def get_send_calldata(self, tokens: List[str], recipients: List[str], values: List[int]) -> str:
        """
        Generate calldata for send(address[] tokens, address[] recipients, uint256[] values) function

        Args:
            tokens (List[str]): List of token addresses
            recipients (List[str]): List of recipient addresses
            values (List[int]): List of values to send
        """
        tokens = [to_checksum_address(addr) for addr in tokens]
        recipients = [to_checksum_address(addr) for addr in recipients]
        return self.contract.encodeABI(
            fn_name='send',
            args=[tokens, recipients, values]
        )


def main():
    """Main function with usage examples"""

    # Contract ABI
    abi_json = '''[{"inputs":[],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[{"internalType":"address","name":"target","type":"address"}],"name":"AddressEmptyCode","type":"error"},{"inputs":[],"name":"FailedCall","type":"error"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"OwnableInvalidOwner","type":"error"},{"inputs":[{"internalType":"address","name":"account","type":"address"}],"name":"OwnableUnauthorizedAccount","type":"error"},{"inputs":[{"internalType":"address","name":"token","type":"address"}],"name":"SafeERC20FailedOperation","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"previousOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferred","type":"event"},{"inputs":[],"name":"ETH_ADDRESS","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes[]","name":"data","type":"bytes[]"}],"name":"multicall","outputs":[{"internalType":"bytes[]","name":"results","type":"bytes[]"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_token","type":"address"},{"internalType":"uint256","name":"_amount","type":"uint256"}],"name":"rescue","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address[]","name":"tokens","type":"address[]"},{"internalType":"address[]","name":"recipients","type":"address[]"},{"internalType":"uint256[]","name":"values","type":"uint256[]"}],"name":"send","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address[]","name":"recipients","type":"address[]"},{"internalType":"uint256[]","name":"values","type":"uint256[]"}],"name":"sendEther","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"contract IERC20","name":"token","type":"address"},{"internalType":"address[]","name":"recipients","type":"address[]"},{"internalType":"uint256[]","name":"values","type":"uint256[]"}],"name":"sendToken","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"}]'''

    # Initialize generator
    generator = ContractCallDataGenerator(abi_json)

    print("=== Contract Call Data Generator ===\n")

    # Example 1: Get ETH_ADDRESS calldata
    eth_address_calldata = generator.get_eth_address_calldata()
    print(f"ETH_ADDRESS() calldata: {eth_address_calldata}")

    # Example 2: Get owner calldata
    owner_calldata = generator.get_owner_calldata()
    print(f"owner() calldata: {owner_calldata}")

    # Example 3: Transfer ownership
    new_owner = "0x44E734ad441C190EDf58E912b58AA6373AB945f8"
    transfer_ownership_calldata = generator.get_transfer_ownership_calldata(new_owner)
    print(f"transferOwnership(address) calldata: {transfer_ownership_calldata}")

    # Example 4: Rescue tokens
    token_address = "0x8d89ca14bcd4107843c62015ba332150e5f11013"
    amount = 2 # 1 token (assuming 18 decimals)
    rescue_calldata = generator.get_rescue_calldata(token_address, amount)
    print(f"rescue(address, uint256) calldata: {rescue_calldata}")

    # Example 5: Send Ether to multiple recipients
    recipients = ["0x3573c0923aecc5bfdcbd3ffd022be96550a23fb4","0xe389b99f5b4bbbcd5247b19e953e4ff86b961ae4"]
    # recipients = [
    #               "0x250d3aa593f0db4588f400ee74b09f20e6fb47af",
    #               "0x5d14046ccc418d41004527b091bce7de4eefde1e",
    #               "0x91e1d5bcd9f919f7a1a541c9fed150de4cdd6720",
    #               "0x5218bc8a3cbd5d65e10095c2573f8b0b5ff1f6eb",
    #               ]

    # values = [1,1]
    values = [1, 1]
    send_ether_calldata = generator.get_send_ether_calldata(recipients, values)
    print(f"sendEther(address[], uint256[]) calldata: {send_ether_calldata}")

    # Example 6: Send tokens to multiple recipients
    # token_contract = "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48"
    token_contract = "0x8d89ca14bcd4107843c62015ba332150e5f11013"
    token_values = [4,5]
     # 0.5 tokens, 1.5 tokens
    send_token_calldata = generator.get_send_token_calldata(token_contract, recipients, token_values)
    print(f"sendToken(address, address[], uint256[]) calldata: {send_token_calldata}")

    # Example 7: Multi-send (different tokens to different recipients)
    tokens = [
        "0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE",  # ETH
        "0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE",  # ETH
        "0x8d89ca14bcd4107843c62015ba332150e5f11013", # Token
        "0x8d89ca14bcd4107843c62015ba332150e5f11013"
    ]
    # tokens = ["0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE", "0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE"]

    send_calldata = generator.get_send_calldata(tokens, recipients, values)
    print(f"send(address[], address[], uint256[]) calldata: {send_calldata}")

    # Example 8: Multicall - combining multiple operations
    # First, prepare individual call data
    call1 = generator.get_owner_calldata()
    call2 = generator.get_eth_address_calldata()


    # Convert hex strings to bytes
    call_data = [ bytes.fromhex(send_token_calldata[2:])]
    multicall_calldata = generator.get_multicall_calldata(call_data)
    print(f"multicall(bytes[]) calldata: {multicall_calldata}")

    # Example 9: Renounce ownership
    renounce_calldata = generator.get_renounce_ownership_calldata()
    print(f"renounceOwnership() calldata: {renounce_calldata}")

    print("\n=== Usage Instructions ===")
    print("1. Install required packages: pip install web3 eth-utils")
    print("2. Use the generated calldata in your transaction")
    print("3. Set appropriate gas limits for each function")
    print("4. For payable functions (send, sendEther), include ETH value in transaction")


def interactive_mode():
    """Interactive mode for custom calldata generation"""
    abi_json = '''[{"inputs":[],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[{"internalType":"address","name":"target","type":"address"}],"name":"AddressEmptyCode","type":"error"},{"inputs":[],"name":"FailedCall","type":"error"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"OwnableInvalidOwner","type":"error"},{"inputs":[{"internalType":"address","name":"account","type":"address"}],"name":"OwnableUnauthorizedAccount","type":"error"},{"inputs":[{"internalType":"address","name":"token","type":"address"}],"name":"SafeERC20FailedOperation","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"previousOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferred","type":"event"},{"inputs":[],"name":"ETH_ADDRESS","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes[]","name":"data","type":"bytes[]"}],"name":"multicall","outputs":[{"internalType":"bytes[]","name":"results","type":"bytes[]"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_token","type":"address"},{"internalType":"uint256","name":"_amount","type":"uint256"}],"name":"rescue","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address[]","name":"tokens","type":"address[]"},{"internalType":"address[]","name":"recipients","type":"address[]"},{"internalType":"uint256[]","name":"values","type":"uint256[]"}],"name":"send","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address[]","name":"recipients","type":"address[]"},{"internalType":"uint256[]","name":"values","type":"uint256[]"}],"name":"sendEther","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"contract IERC20","name":"token","type":"address"},{"internalType":"address[]","name":"recipients","type":"address[]"},{"internalType":"uint256[]","name":"values","type":"uint256[]"}],"name":"sendToken","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"}]'''

    generator = ContractCallDataGenerator(abi_json)

    print("=== Interactive Call Data Generator ===")
    print("Available functions:")
    print("1. ETH_ADDRESS()")
    print("2. owner()")
    print("3. renounceOwnership()")
    print("4. transferOwnership(address)")
    print("5. rescue(address, uint256)")
    print("6. sendEther(address[], uint256[])")
    print("7. sendToken(address, address[], uint256[])")
    print("8. send(address[], address[], uint256[])")
    print("9. multicall(bytes[])")
    print("0. Exit")

    while True:
        try:
            choice = input("\nEnter function number (0-9): ")

            if choice == '0':
                break
            elif choice == '1':
                print(f"Calldata: {generator.get_eth_address_calldata()}")
            elif choice == '2':
                print(f"Calldata: {generator.get_owner_calldata()}")
            elif choice == '3':
                print(f"Calldata: {generator.get_renounce_ownership_calldata()}")
            elif choice == '4':
                new_owner = input("Enter new owner address: ")
                print(f"Calldata: {generator.get_transfer_ownership_calldata(new_owner)}")
            elif choice == '5':
                token = input("Enter token address: ")
                amount = int(input("Enter amount: "))
                print(f"Calldata: {generator.get_rescue_calldata(token, amount)}")
            elif choice == '6':
                recipients = input("Enter recipient addresses (comma-separated): ").split(',')
                values = [int(x) for x in input("Enter values (comma-separated): ").split(',')]
                print(f"Calldata: {generator.get_send_ether_calldata(recipients, values)}")
            elif choice == '7':
                token = input("Enter token address: ")
                recipients = input("Enter recipient addresses (comma-separated): ").split(',')
                values = [int(x) for x in input("Enter values (comma-separated): ").split(',')]
                print(f"Calldata: {generator.get_send_token_calldata(token, recipients, values)}")
            elif choice == '8':
                tokens = input("Enter token addresses (comma-separated): ").split(',')
                recipients = input("Enter recipient addresses (comma-separated): ").split(',')
                values = [int(x) for x in input("Enter values (comma-separated): ").split(',')]
                print(f"Calldata: {generator.get_send_calldata(tokens, recipients, values)}")
            else:
                print("Invalid choice. Please try again.")

        except Exception as e:
            print(f"Error: {e}")


if __name__ == "__main__":
    # Run main examples
    main()

    # Optionally run interactive mode
    # run_interactive = input("\nRun interactive mode? (y/n): ")
    # if run_interactive.lower() == 'y':
    #     interactive_mode()
```


# Estimate transaction fees
Source: https://cobo.com/developers/v2/guides/transactions/estimate-fees

Guide on estimating transaction fees in WaaS 2.0, including factors affecting fees and calculation methods.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Transaction fees are essential for processing and validating transactions on a blockchain network. They ensure network security, incentivize validators, and maintain efficiency. The method of calculating these fees depends on the blockchain's design and current network conditions. Cobo offers specific features to streamline transaction fee estimation for users.

* When you make a transfer on Cobo Portal, you can see the estimated transaction fee on the UI.
* You can call the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) API operation.

<Note>The estimated transaction fee reflects current network conditions and may change by the time the actual transaction is processed.</Note>

When you call the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) operation, you need to specify the following parameters:

* `request_type`: The type of transaction, which can be a transfer or a contract call.
* `source`: The transaction source.
* `destination`: The transaction destination.
* (Only required for transfers) `token_id`: The ID of the token being transferred.
* (Only required for contract calls) `chain_id`: The ID of the chain on which the smart contract is deployed.

You will get the estimated transaction fee with different fee levels in the response, which varies based on the blockchain network and the fee model used.

## Fee models

Each blockchain may employ multiple fee models to calculate transaction fees. For EVM chains, both the Legacy and EIP-1559 models are supported.

Most transactions follow the blockchain's native fee model. However, transactions from Custodial Wallets (Asset Wallets) and Exchange Wallets always use the [fixed fee model](#chains-using-the-fixed-model). If you specify a different fee model when initiating a transaction from these wallets, the API request will return an error.

### EVM chains

#### EIP-1559 model

The following chains currently support [EIP-1559](https://eips.ethereum.org/EIPS/eip-1559):

* Ethereum Mainnet
* Sepolia Testnet
* Scroll Mainnet
* Base
* BNB Smart Chain
* Polygon
* Sonic
* Berachain

In the EIP-1559 model, the transaction fee is calculated as: (base fee per gas + priority fee per gas) \* gas limit

| Parameter            | Description                                                                                                                                                |
| -------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------- |
| Base fee per gas     | The minimum fee required to include a transaction in a block per gas unit used on the chain. It is dynamically adjusted based on network demand.           |
| Priority fee per gas | An additional fee paid to miners/validators to prioritize the transaction per gas unit used on the chain (also known as a tip).                            |
| Gas limit            | The maximum number of gas units you are willing to spend to execute the transaction or run the EVM. Different operations consume different amounts of gas. |

<Note>For the Legacy and EIP-1559 fee models, an additional fee is charged for submitting transaction calldata to L1 (Layer 1). This fee is reflected in the API response under the `reserved_fee` field.</Note>

You can customize the following values:

* Max fee per gas: The maximum fee per gas unit you are willing to pay.
* Max priority fee per gas: The maximum priority fee per gas unit you are willing to pay.
* Gas limit

Refer to the response of the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) operation for details.

#### Legacy model

All EVM chains support the Legacy model.

In the Legacy model, the transaction fee is calculated as: gas price \* gas limit

| Parameter | Description                                                                                                                                                |
| --------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------- |
| Gas price | The gas price, in wei, representing the amount of ETH that must be paid to validators per gas unit used to process the transaction.                        |
| Gas limit | The maximum number of gas units you are willing to spend to execute the transaction or run the EVM. Different operations consume different amounts of gas. |

<Note>For the Legacy and EIP-1559 fee models, an additional fee is charged for submitting transaction calldata to L1 (Layer 1). This fee is reflected in the API response under the `reserved_fee` field.</Note>

You can customize the following values:

* Gas price
* Gas limit

Refer to the response of the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) operation for details.

### UTXO-based chains

Currently supported chains include:

* Bitcoin
* Cardano
* Nervos CKB
* Handshake

In the UTXO-based model, the transaction fee is calculated as: fee rate \* transaction size

| Parameter        | Description                                                                                                       |
| ---------------- | ----------------------------------------------------------------------------------------------------------------- |
| Fee rate         | The fee rate, in sats/vByte, representing how many satoshis you are willing to pay per vByte of transaction data. |
| Transaction size | The total size of a transaction on-chain in bytes, which impacts the total fee in UTXO models.                    |

You can customize the following values:

* Fee rate
* Max fee amount

Refer to the response of the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) operation for details.

### Solana

On Solana, you can use either the native model or the Legacy model. In the native model, the transaction fee is calculated as: base fee + (CU price \* CU limit)

| Parameter | Description                                                                                                                                                                                                                |
| --------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| Base fee  | A fixed fee charged per signature (default 5,000 lamports per signature).                                                                                                                                                  |
| CU price  | The price paid per CU (compute unit) to increase transaction priority, in lamports.                                                                                                                                        |
| CU limit  | The maximum number of compute units your transaction is allowed to consume. A higher limit may increase priority but also increases the fee.                                                                               |
| Rent      | A one-time fee required to activate a Solana token sub-address (Associated Token Account, or ATA) before that token can be used. It is not included in the base fee or compute unit fee and is paid by the source address. |

You can customize the following values:

* CU price
* CU limit

Refer to the response of the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) operation for details.

<Note>Activating a Solana token sub-address (Associated Token Account) incurs a one-time rent paid by the source address, separate from the network transaction fee. For details, see [Solana token account rent](/developers/v2/guides/transactions/solana-token-account-rent).</Note>

<Note>Solana and Filecoin both support two fee models: their native model and the Legacy model. When calling transaction API operations, you can choose which model to use. However, for Replace-By-Fee (RBF) transactions, you must use the same fee model as the original transaction.</Note>

### Filecoin

On Filecoin, you can use either the native model or the Legacy model. In the native model, the transaction fee is calculated as: min(gas fee cap, base fee + gas premium) \* gas limit

| Parameter   | Description                                                                                                                                         |
| ----------- | --------------------------------------------------------------------------------------------------------------------------------------------------- |
| Gas fee cap | The maximum gas price you are willing to pay per unit.                                                                                              |
| Base fee    | The minimum fee required for inclusion in a block. It is dynamically adjusted based on network congestion and is burned to reduce total FIL supply. |
| Gas premium | A user-defined tip to incentivize miner prioritization.                                                                                             |
| Gas limit   | The maximum amount of gas your transaction can consume.                                                                                             |

You can customize the following values:

* Gas fee cap
* Gas premium
* Gas limit

Refer to the response of the [Estimate transaction fee](/developers/v2/api-references/transactions/estimate-transaction-fee) operation for details.

<Note>Solana and Filecoin both support two fee models: their native model and the Legacy model. When calling transaction API operations, you can choose which model to use. However, for Replace-By-Fee (RBF) transactions, you must use the same fee model as the original transaction.</Note>

### Chains using the fixed model

The following chains use a fixed fee model:

* TRON
* Algorand
* Polkadot
* Internet Computer and its ICRC assets (ckBTC, ckETH, ckUSDC, ckUSDT, DKP, GLDGOV, ICS, NICP, OC, OGY)
* Stellar
* Ripple
* Tezos
* Sui
* Near

In the fixed model, the transaction fee is a fixed amount. You can customize the parameter Max fee amount to cap the maximum fee for a transaction.

## Fee levels

Transaction fees are influenced by speed levels. Users can choose between slow, recommended, and fast transaction speeds, with faster speeds incurring higher fees.

Cobo supports three fee levels for Legacy, EIP-1559, UTXO, Solana and Filecoin models:

* Slow: Lower fee for slower processing.
* Recommended: Balanced fee and confirmation time.
* Fast: Higher fee for quicker processing.

## Replace-By-Fee (RBF) transaction fee

Replace-By-Fee (RBF) is a feature that allows you to replace an unconfirmed transaction with a new version that typically pays a higher transaction fee. This functionality provides flexibility to modify transactions after they are broadcast but before they are confirmed by miners. For more details, refer to [Replace-By-Fee (RBF) transactions](/developers/v2/guides/transactions/manage-transactions#replace-by-fee-rbf-transactions).

The logic for estimating RBF transaction fees is similar to that for normal transactions, with the addition of a fee increase for the RBF transaction. The key points to consider when estimating RBF transaction fees based on different fee models are as follows:

* Legacy: Increase the gas price. The gas price for an RBF transaction must be higher than that of the transaction being replaced.
* EIP-1559: Increase both the max fee per gas and max priority fee per gas.
* UTXO: Increase the fee rate and ensure that the product of the fee rate and transaction size is greater than that of the original transaction. If not, the node might reject broadcasting the transaction.
* Fixed: Increase the fee amount.
* Filecoin: It is recommended to increase both gas premium and gas fee cap by 25%.

## Fees on Layer 2 chains

On Layer 2 (L2) chains such as Arbitrum, network fees can change rapidly. If fees rise sharply after you submit a transaction, the transaction can remain in the `PendingSignature` or `Broadcasting` status longer than expected. How you unblock it depends on the status:

* `Broadcasting`: The transaction is already broadcast. Use the Replace-By-Fee (RBF) speed-up operation to rebroadcast it with a higher fee. To raise the fee, use the [Speed up transaction](/developers/v2/api-references/transactions/speed-up-transaction) operation. For how RBF works end to end, see [RBF (Replace-By-Fee) transaction lifecycle](/developers/v2/guides/transactions/rbf-transaction-lifecycle).
* `PendingSignature`: The transaction is not yet broadcast, so RBF does not apply. The transaction must be signed within a limited signing window; if signing does not complete in time, it fails with the sub-status `FailedSignerTimeout`. In that case, submit a new transaction to try again. For details, see [Transaction statuses and sub-statuses](/developers/v2/guides/transactions/status).

## How Cobo estimate the fees

Below is how Cobo calculates the fees for each model:

| Fee Model                                           | Estimation Method                                                                                                                                                                                                                                                                                                  |
| --------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| Legacy                                              | <ul><li>Gas price: Calculated based on third-party nodes and self-managed nodes.</li><li>Gas limit: Queried from the corresponding node based on the source and destination.</li></ul>                                                                                                                             |
| [EIP-1559](https://eips.ethereum.org/EIPS/eip-1559) | <ul><li>Maximum gas fee per gas unit: Calculated based on third-party nodes and self-managed nodes.</li><li>Maximum priority fee per gas unit: Calculated based on third-party nodes and self-managed nodes.</li><li>Gas limit: Queried from the corresponding node based on the source and destination.</li></ul> |
| UTXO                                                | <ul><li>Fee rate: Calculated based on third-party nodes and self-managed nodes.</li><li>Transaction size: Calculated based on the source spendables (UTXOs) and destination.</li></ul>                                                                                                                             |
| Fixed                                               | <ul><li>Fixed fee amount: Calculated based on self-managed nodes.</li></ul>                                                                                                                                                                                                                                        |


# Manage transactions
Source: https://cobo.com/developers/v2/guides/transactions/manage-transactions

Comprehensive guide on managing transactions in WaaS 2.0, covering canceling, speeding up, and dropping transactions.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This guide outlines the processes for canceling, speeding up, and dropping transactions. By mastering these techniques, you can ensure that your transactions are processed promptly and accurately.

## Paginate the transaction list

The [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) operation returns results one page at a time. Pagination is controlled by two separate cursor parameters, `before` and `after`, which move the page window in opposite directions. The `direction` parameter is unrelated to paging and only controls sort order.

* `after`: Pages forward to the next page. Pass the `after` value returned in the `pagination` object of the previous response.
* `before`: Pages backward to the previous page. Pass the `before` value returned in the `pagination` object of the previous response.

On your first request, do not include either `before` or `after`. Cobo returns the first page together with a `pagination` object that contains the `before` and `after` cursor values you use to navigate from it. Use the `limit` parameter to set the number of records per page.

<Note>The `direction` parameter is a separate sort control and does not move the page window. It accepts `ASC` (ascending, the default) or `DESC` (descending), and only determines the order in which records are returned. Paging forward and backward is always controlled by `after` and `before`.</Note>

### Pagination walkthrough

1. Send the first request with no `before` and no `after` parameter. The response returns the first page and a `pagination` object containing `before`, `after`, and `total_count`.
2. To move forward to the next page, send another request with `after` set to the `after` value from the previous response.
3. To move backward to the previous page, send another request with `before` set to the `before` value from the previous response.
4. When the response returns an empty `after` value, you have reached the end of the results. When the response returns an empty `before` value, you have reached the start of the results.

## Cancel a transaction

Canceling a transaction stops it while it is still pending.

You might want to cancel a transaction if it was initiated by mistake, if you need to modify its details, or if it no longer needs to be executed. Canceling prevents the transaction from being processed further.

<Note>This operation only applies to transactions from MPC Wallets.</Note>

A transaction can be cancelled if its status is either of the following:

* `Submitted`
* `PendingScreening`
* `PendingAuthorization`
* `PendingSignature` (Only when the sub-status is `Queue`, `InsufficientBalance`, `InsufficientBalanceFundLocked`, `PendingSignerApproval`, `PendingSystemProcessing`, or `Built`)

To cancel a transaction via the WaaS 2.0 API, use the [Cancel transaction](/developers/v2/api-references/transactions/cancel-transaction) operation. This requires the transaction ID of the transaction you wish to cancel.

## Replace-By-Fee (RBF) transactions

Replace-By-Fee (RBF) is a feature that allows you to replace an unconfirmed transaction with a new version that typically pays a higher transaction fee. This functionality provides flexibility to modify transactions after they are broadcast but before they are confirmed by miners. The key benefits of RBF include the ability to:

* Accelerate transaction confirmation by increasing the fee.
* Cancel a pending transaction.
* Modify transaction details such as the destination address or transfer amount.

The two most common use cases of RBF are speeding up and dropping transactions.

For how a replaced transaction's status changes and the events it emits, see [RBF (Replace-By-Fee) transaction lifecycle](/developers/v2/guides/transactions/rbf-transaction-lifecycle).

### Speed up a transaction

Speeding up a transaction leverages RBF to replace the original transaction with a version with a higher fee, encouraging miners to prioritize it for faster confirmation.

You might want to speed up a transaction if it is taking too long to be confirmed due to low fees. This is particularly useful in times of network congestion.

<Note>This operation only applies to transactions from Custodial Wallets (Web3 Wallets) and MPC Wallets. It does not apply to transactions on the following chains: VET, TRON, TVET, SOL, and TON.</Note>

A transaction can be sped up only if its status is `Broadcasting`.

To speed up a transaction, use the [Speed up transaction](/developers/v2/api-references/transactions/speed-up-transaction) operation. This requires the transaction ID of the transaction you wish to speed up.

### Drop a transaction

Dropping a transaction leverages RBF to replace the original transaction with a version that effectively cancels it.

* For EVM chains, this RBF transaction has a transfer amount of `0` and the sending address is the same as the receiving address.
* For UTXO chains, this RBF transaction has a transfer amount of `0` and the destination address is the same as the change address in the original transaction.

You might want to drop a transaction if it was initiated by mistake, if you need to modify its details, or if it no longer needs to be executed but it cannot be canceled.

<Note>This operation only applies to transactions from Custodial Wallets (Web3 Wallets) and MPC Wallets. It does not apply to transactions on the following chains: VET, TRON, TVET, SOL, and TON.</Note>

A transaction can be dropped only if its status is `Broadcasting`.

To drop a transaction, use the [Drop transaction](/developers/v2/api-references/transactions/drop-transaction) operation. This requires the transaction ID of the transaction you wish to drop.

When a transaction is being dropped, any subsequent drop or speed up operations will still apply to the original transaction. For example, if a user creates Transaction A and later performs a drop operation on Transaction A using Transaction B, followed by a speed up operation on Transaction B using Transaction C, the speed up operation will still apply to Transaction A, not Transaction B.

## Cobo-defined categories

This field `cobo_category` is defined by Cobo to indicate the logical category or purpose of a transaction, helping users identify what type of operation the transaction belongs to.

### Fee Station related

| Category            | Description                                                                           |
| ------------------- | ------------------------------------------------------------------------------------- |
| AutoFueling         | A transaction where Fee Station pays the gas fee.                                     |
| AutoFuelingRefund   | A transaction where Fee Station refunds a previously paid gas fee.                    |
| BillPayment         | A transaction where Fee Station pays Cobo Bills.                                      |
| BillRefund          | A transaction where Fee Station refunds previously paid Cobo Bills.                   |
| GasFeeSponsor       | A transaction where Fee Station pays the gas fee using USD stablecoins.               |
| GasFeeSponsorRefund | A transaction where Fee Station refunds a gas fee previously paid in USD stablecoins. |
| CommissionFeeCharge | A transaction where Fee Station pays the commission fee.                              |
| CommissionFeeRefund | A transaction where Fee Station refunds a previously paid commission fee.             |

<Note>Fee Station transactions, including their categories, can be retrieved only through [Get Fee Station transaction information](/developers/v2/api-references/feestation/get-fee-station-transaction-information) and [List all Fee Station transactions](/developers/v2/api-references/feestation/list-all-fee-station-transactions).</Note>

### Screening related

| Category          | Description                                                   |
| ----------------- | ------------------------------------------------------------- |
| ScreenAppRefund   | A refund transaction initiated through the Screening App.     |
| ScreenAppIsolate  | An isolation transaction initiated through the Screening App. |
| ComplianceRefund  | A refund transaction initiated by Cobo KYT.                   |
| ComplianceIsolate | An isolation transaction initiated by Cobo KYT.               |

### Staking related

| Category                     | Description                                                     |
| ---------------------------- | --------------------------------------------------------------- |
| StakingBabylonBtcDelegation  | A transaction for delegating BTC in Babylon staking.            |
| StakingBabylonBtcSignBabylon | A transaction for signing Babylon operations with BTC.          |
| StakingBabylonClaim          | A transaction for claiming rewards from Babylon staking.        |
| StakingBabylonSlashing       | A transaction related to slashing penalties in Babylon staking. |
| StakingBabylonStake          | A transaction for staking assets in the Babylon platform.       |
| StakingBabylonUnstake        | A transaction for unstaking assets from the Babylon platform.   |
| StakingBabylonWithdraw       | A transaction for withdrawing assets from Babylon staking.      |
| StakingBithiveClaim          | A transaction for claiming rewards from BitHive staking.        |
| StakingBithiveStake          | A transaction for staking assets in the BitHive platform.       |
| StakingBithiveUnstake        | A transaction for unstaking assets from the BitHive platform.   |
| StakingBithiveWithdraw       | A transaction for withdrawing assets from BitHive staking.      |
| StakingCoreStake             | A transaction for staking assets in the Core staking platform.  |
| StakingCoreWithdraw          | A transaction for withdrawing assets from Core staking.         |
| StakingEthClaim              | A transaction for claiming rewards from ETH staking.            |
| StakingEthStake              | A transaction for staking ETH assets.                           |
| StakingEthUnstake            | A transaction for unstaking ETH assets.                         |
| StakingSkyfarmClaim          | A transaction for claiming rewards from Skyfarm staking.        |
| StakingSkyfarmStake          | A transaction for staking assets in the Skyfarm platform.       |
| StakingSkyfarmUnstake        | A transaction for unstaking assets from the Skyfarm platform.   |

### Other categories

| Category               | Description                                                                                                                                                                                          |
| ---------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| AutoSweep              | A transaction where tokens are automatically swept to a consolidated address.                                                                                                                        |
| Tokenization           | A transaction for managing tokenized assets, such as minting or wrapping tokens, through the Tokenization app.                                                                                       |
| TokenizationGasSponsor | A transaction where gas fees are sponsored for tokenization-related operations, ensuring the transaction proceeds even if the source address lacks sufficient balance, through the Tokenization app. |
| TokenSwap              | A transaction for token swapping or cross-chain bridging through the Token Swap app.                                                                                                                 |
| StellarChangeTrust     | A transaction for establishing a trustline on the Stellar network.                                                                                                                                   |
| NonceAccountSign       | A transaction signed using a Solana nonce account, enabling deterministic and replay-safe transaction execution on the Solana network.                                                               |
| FeePayerSign           | A transaction where a designated Solana fee payer account covers the transaction fees, separating the fee payment from the main signer or source account.                                            |


# RBF (Replace-By-Fee) transaction lifecycle
Source: https://cobo.com/developers/v2/guides/transactions/rbf-transaction-lifecycle

Understand how Replace-By-Fee (RBF) replaces an unconfirmed transaction, how the original transaction's status changes, and the events you receive.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## Overview

Replace-By-Fee (RBF) replaces an unconfirmed, already-broadcast transaction with a new version. This guide describes the full lifecycle of an RBF replacement: the replacement operations you can perform, how the original transaction's status changes, and the events you receive.

For the step-by-step operations, see [Manage transactions](/developers/v2/guides/transactions/manage-transactions). For the fee rules that apply to RBF transactions, see [Estimate transaction fees](/developers/v2/guides/transactions/estimate-fees#replace-by-fee-rbf-transaction-fee).

## Replacement operations

WaaS 2.0 supports the following RBF operations:

* **Speed up**: Replaces the original transaction with a higher-fee version so that it confirms faster. Use the [Speed up transaction](/developers/v2/api-references/transactions/speed-up-transaction) operation.
* **Drop**: Replaces the original transaction with a version that effectively cancels it. Use the [Drop transaction](/developers/v2/api-references/transactions/drop-transaction) operation.

Both operations apply only when the original transaction is in the `Broadcasting` status. They do not apply to transactions on the following chains: VET, TRON, TVET, SOL, and TON.

## Original transaction status after replacement

When a replacement transaction takes effect, the original transaction moves to the `Failed` status with the sub-status `ReplacedByNewTransaction`. For the complete list of statuses and sub-statuses, see [Transaction statuses and sub-statuses](/developers/v2/guides/transactions/status).

## Chained replacements

Any subsequent drop or speed-up operations continue to apply to the original transaction. For example, if you create Transaction A, perform a drop operation on Transaction A using Transaction B, and then perform a speed-up operation on Transaction B using Transaction C, the speed-up operation still applies to Transaction A, not Transaction B.

## Events

RBF status changes are surfaced through the WaaS 2.0 transaction webhook events. Subscribe to the `wallets.transaction.updated` event, which covers the full transaction lifecycle including failure. For details, see [Webhook event types](/developers/v2/guides/webhooks-callbacks/webhook-event-type).

## Related guides

* [Manage transactions](/developers/v2/guides/transactions/manage-transactions)
* [Estimate transaction fees](/developers/v2/guides/transactions/estimate-fees)
* [Transaction statuses and sub-statuses](/developers/v2/guides/transactions/status)
* [Transaction sources and destinations](/developers/v2/guides/transactions/sources-and-destinations)


# Swap tokens on Solana using Jupiter
Source: https://cobo.com/developers/v2/guides/transactions/sol-jupiter-swap

A complete example guide for integrating Cobo WaaS SDK with Jupiter to perform token swaps on Solana.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This guide uses a complete Python example to demonstrate how to combine Cobo WaaS SDK with Jupiter on Solana, from getting swap routes to submitting an on-chain token swap transaction, so that you can quickly integrate token swap capabilities.

<Note>This document is intended for developers who already understand Solana programming and Jupiter routing. Basic blockchain concepts and Jupiter mechanics will not be introduced here.</Note>

## Prerequisites

Before you begin, ensure the following:

* You have followed the steps in [Send your first API request](/developers/v2/guides/get-started/get-started-with-waas) and successfully sent an API request.
* You understand and can use the [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract) API.
* You are familiar with Solana smart contract calls and understand the basic concepts and usage of Jupiter.
* Your Solana address has sufficient balance, including:
  * Enough balance of the token you plan to swap;
  * Enough SOL to pay for transaction fees.
* Since this guide provides a Python-based example, please ensure your local environment has:
  * Python 3.9 or above
  * Required packages: `cobo_waas2`, `requests`, and `solders`
* This example uses an MPC Wallet (Organization-Controlled Wallet). If you are using a Custodial Wallet (Web3 wallet), make sure to update the `source` parameter in the Call Smart Contract API request to use the Custodial Wallets (Web3 wallets) structure instead.

## Python example

This example walks through:

1. Getting the best swap route from Jupiter
2. Generating swap instructions with Jupiter
3. Parsing Address Lookup Tables (ALT)
4. Call smart contract
5. Executing a swap from SOL to USDT

The following code highlights the parameters you must customize (such as API key, wallet ID, address, token pair, and amount). All other code can be used without modification.

```python highlight={265, 267, 269, 271, 276} theme={null}
import base64
import cobo_waas2
import json
import requests
import uuid

from solders.pubkey import Pubkey


# ========= Jupiter configuration =========
JUPITER_BASE_URL = "https://lite-api.jup.ag/swap/v1/"
SOLANA_RPC = "https://api.mainnet-beta.solana.com"

# Fixed mint addresses for Solana mainnet tokens. Native SOL uses a special system-defined mint address.
SOL_MINT = "So11111111111111111111111111111111111111112"
JLP_MINT = "27G8MtK7VtTcCHkpASjSDdkWWYfoqT6ggEuKidVJidD4"
USDC_MINT = "EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v"
USDT_MINT = "Es9vMFrzaCERmJfrF4H2FYD4KCoNkY11McCe8BenwNYB"

COIN_MINT_MAP = {
    'SOL': SOL_MINT,
    'SOL_JLP': JLP_MINT,
    'SOL_USDC': USDC_MINT,
    'SOL_USDT': USDT_MINT,
}
COIN_DECIMALS = {
    SOL_MINT: 9,
    JLP_MINT: 6,
    USDC_MINT: 6,
    USDT_MINT: 6,
}


# ========= Jupiter API section (calling Jupiter quote/swap APIs) =========
def get_jupiter_quote(input_mint, output_mint, amount, slippage_bps=50):
    """
    Request a swap quote from Jupiter.
    Args:
        input_mint: Mint address of the input token
        output_mint: Mint address of the output token
        amount: Swap amount
        slippage_bps: Slippage tolerance
    """
    params = {
        "inputMint": input_mint,
        "outputMint": output_mint,
        "amount": str(amount),
        "slippageBps": str(slippage_bps)
    }
    r = requests.get(JUPITER_BASE_URL + "quote", params=params, verify=False)
    r.raise_for_status()
    return r.json()


def get_swap_instructions(quote, address):
    """
    Generate swap instructions based on a Jupiter quote.
    """
    payload = {
        "quoteResponse": quote,
        "userPublicKey": address,
        "dynamicSlippage": True,
        "useSharedAccounts": True,
        "dynamicComputeUnitLimit": True,
        "wrapAndUnwrapSol": True,
        "skipUserAccountsRpcCalls": False,
    }
    r = requests.post(JUPITER_BASE_URL + "swap-instructions", json=payload, verify=False)
    r.raise_for_status()
    return r.json()


def fetch_address_lookup_table(alt_address):
    """
    Fetch accounts inside the Address Lookup Table (ALT).
    Args:
        alt_address: ALT address
    Returns:
        list: List of addresses inside the ALT
    """
    print(f"  Fetching ALT: {alt_address}")

    payload = {
        "jsonrpc": "2.0",
        "id": 1,
        "method": "getAccountInfo",
        "params": [
            alt_address,
            {"encoding": "base64"}
        ]
    }

    try:
        response = requests.post(SOLANA_RPC, json=payload, verify=False)
        response.raise_for_status()
        result = response.json()

        if "result" not in result or not result["result"] or not result["result"]["value"]:
            print(f"  Warning: Unable to fetch ALT account info: {alt_address}")
            return []

        # Parsing ALT account information
        account_data = result["result"]["value"]["data"][0]
        raw_data = base64.b64decode(account_data)

        # ALT account layout:   
        # - The first 56 bytes are header metadata
        # - Every subsequent 32-byte chunk is a public key inside the lookup table
        addresses = []
        offset = 56  # Skip the header

        while offset + 32 <= len(raw_data):
            pubkey_bytes = raw_data[offset:offset + 32]
            pubkey = Pubkey(pubkey_bytes)
            addresses.append(str(pubkey))
            offset += 32

        print(f"  Found {len(addresses)} accounts in ALT")
        return addresses
    except Exception as e:
        print(f"  ALT fetch failed: {e}")
        return []


# ========= Cobo API section =========
class CoboAPI:
    def __init__(self, api_private_key, host):
        self.api_private_key = api_private_key
        self.host = host

    def get_configuration(self):
        return cobo_waas2.Configuration(
            api_private_key=self.api_private_key,
            host=self.host
        )

    def swap_coin(self, wallet_id, address, input_coin, output_coin, amount):
        """
        Call Cobo WaaS service to execute a Solana contract call for a token swap.
        Args:
            wallet_id: Cobo wallet ID
            address: Solana address
            input_coin: Input token symbol
            output_coin: Output token symbol
            amount: Swap amount
        Returns:
            transaction_id: Transaction ID in Cobo Portal
        """
        print(f"Executing token swap via Cobo WaaS... address={address}, {input_coin} -> {output_coin}, amount={amount}")

        input_mint = COIN_MINT_MAP[input_coin]
        output_mint = COIN_MINT_MAP[output_coin]
        amount = self.to_jupiter_amount(amount, COIN_DECIMALS[input_mint])

        with cobo_waas2.ApiClient(self.get_configuration()) as api_client:
            # 1. Get a quote from Jupiter
            quote = get_jupiter_quote(input_mint, output_mint, amount)

            # 2. Get swap instructions from Jupiter
            instructions_json = get_swap_instructions(quote, address)

            # 3. Build transaction instructions and ALT accounts
            instructions, alt_accounts = self.build_transaction(instructions_json, address)

            # 4. Call Cobo WaaS service to create a contract call transaction
            contract_call_params = cobo_waas2.ContractCallParams(
                request_id=str(uuid.uuid4()),
                chain_id="SOL",
                source=cobo_waas2.ContractCallSource(
                    cobo_waas2.MpcContractCallSource(
                        source_type=cobo_waas2.ContractCallSourceType.ORG_CONTROLLED,
                        wallet_id=wallet_id,
                        address=address,
                    )
                ),
                destination=cobo_waas2.ContractCallDestination(
                    cobo_waas2.SolContractCallDestination(
                        destination_type=cobo_waas2.ContractCallDestinationType.SOL_CONTRACT,
                        instructions=instructions,
                        address_lookup_table_accounts=alt_accounts
                    )
                ),
            )

            print("=================================")
            print("contract call params:", contract_call_params.to_json())
            print("=================================")

            api_instance = cobo_waas2.TransactionsApi(api_client)

            try:
                api_response = api_instance.create_contract_call_transaction(
                    contract_call_params=contract_call_params
                )
                print("contract call response:", api_response)
                return api_response.transaction_id
            except Exception as e:
                print("Error:", e)
                return ""

    @staticmethod
    def build_instruction(ins, address):
        accounts = []
        print("build instruction:", ins.get("programId"), "accounts:", len(ins.get("accounts", [])))
        for acc in ins["accounts"]:
            accounts.append(
                cobo_waas2.SolContractCallAccount(
                    pubkey=acc["pubkey"],
                    is_signer=acc["isSigner"],
                    is_writable=acc["isWritable"] or acc["pubkey"] == address,
                )
            )
        return cobo_waas2.SolContractCallInstruction(
            program_id=ins["programId"],
            accounts=accounts,
            data=ins["data"],
        )

    def build_transaction(self, instructions_json, address):
        print("build transaction:", json.dumps(instructions_json))
        all_instructions = []

        for key in ["computeBudgetInstructions", "setupInstructions"]:
            all_instructions += [self.build_instruction(i, address) for i in instructions_json.get(key, [])]

        if "swapInstruction" in instructions_json and instructions_json["swapInstruction"]:
            all_instructions.append(self.build_instruction(instructions_json["swapInstruction"], address))

        if "cleanupInstruction" in instructions_json and instructions_json["cleanupInstruction"]:
            all_instructions.append(self.build_instruction(instructions_json["cleanupInstruction"], address))

        if "otherInstructions" in instructions_json and instructions_json["otherInstructions"]:
            all_instructions += [self.build_instruction(i, address) for i in instructions_json["otherInstructions"]]

        alt_accounts = []

        if "addressLookupTableAddresses" in instructions_json:
            alt_addresses = instructions_json["addressLookupTableAddresses"]
            for alt_address in alt_addresses:
                addresses = fetch_address_lookup_table(alt_address)
                if addresses:
                    alt_accounts.append(
                        cobo_waas2.SolContractCallAddressLookupTableAccount(
                            alt_account_key=alt_address,
                            addresses=addresses,
                        )
                    )

        return all_instructions, alt_accounts

    @staticmethod
    def to_jupiter_amount(readable_amount, decimals):
        """Convert human-readable amount to Jupiter integer amount."""
        return int(readable_amount * (10 ** decimals))

    @staticmethod
    def to_readable_amount(raw_amount, decimals):
        """Convert Jupiter integer amount to human-readable format."""
        return raw_amount / (10 ** decimals)


if __name__ == "__main__":
    # ======== Parameters you must modify for your own environment (required) ========
    # TODO: Use the development environment. For production environment, change to "https://api.cobo.com/v2".
    cobo_host = "https://api.dev.cobo.com/v2"
    # TODO: Enter your API key
    api_key = ""
    # TODO: Enter your Wallet ID
    mpc_wallet_id = ""
    # TODO: Enter your Solana address, and make sure it has enough SOL and the token to be swapped
    sol_address = ""

    # ======== Example: SOL -> USDT ========
    myCoboApi = CoboAPI(api_key, cobo_host)
    # "SOL" is the token ID of input token, "SOL_USDT" is the token ID of output token (USDT), 0.0001 is the swap amount
    myCoboApi.swap_coin(mpc_wallet_id, sol_address, "SOL", "SOL_USDT", 0.0001)
    # If you want to swap to JLP or USDC, use the following examples:
    # myCoboApi.swap_coin(mpc_wallet_id, sol_address, "SOL", "SOL_JLP", 0.0001)
    # myCoboApi.swap_coin(mpc_wallet_id, sol_address, "SOL", "SOL_USDC", 0.0001)

```


# Solana token account rent
Source: https://cobo.com/developers/v2/guides/transactions/solana-token-account-rent

How Solana Associated Token Account (ATA) rent works, who pays it, and what to expect in transaction records.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

On Solana, each token is held in its own sub-address called an Associated Token Account (ATA). When sending tokens to an address that has never received SOL or that specific token before, the sending address must pay a one-time activation fee — called rent — to create and activate the ATA before the transfer can complete.

The following points are important when working with Solana token transfers:

**Rent is paid by the sending address**

If the recipient has not previously received SOL or a specific token, the source (sending) address pays extra rent to create and activate the token's ATA (sub-address). This is separate from the normal Solana network transaction fee.

**`fee_used` does not include rent**

The `fee_used` field in a Solana transaction record covers only the on-chain network transaction fee and does not include rent. For details, see [Estimate transaction fees](/developers/v2/guides/transactions/estimate-fees).

**Rent is not parsed from completed transactions**

When Cobo processes a completed on-chain transaction, `rent_amount` is not extracted from the transaction data. As a result:

* The `rent_amount` field in completed transaction records will not reflect the actual rent charged.
* No deposit record is created for the rent transfer to the sub-address.
* No `wallets.addresses.created` or `wallets.transaction.*` webhook event is emitted for the rent payment.


# Transaction sources and destinations
Source: https://cobo.com/developers/v2/guides/transactions/sources-and-destinations

Overview of transaction sources and destinations in WaaS 2.0.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

In WaaS 2.0, every transaction involves a source and a destination. The source indicates where the transaction originates, while the destination represents where the transaction is going, such as a wallet address, a signature, a contract, and more. Each transaction type corresponds to a specific set of source and destination types. For example, in a withdrawal transaction, the source will be a wallet created on Cobo Portal, and the destination will be either a wallet address or an Exchange Wallet.

## Source and destination for each transaction type

Refer to the following table for the source and destination types corresponding to each transaction type. Detailed definitions for each source type and destination type can be found below the table.

<Note>If you transfer tokens between two wallets created on Cobo Portal, two transactions will be recorded: a deposit into the destination wallet and a withdrawal from the source wallet.</Note>

To control whether a transfer is routed internally through Cobo Loop or on-chain, see [Transfer routing](/developers/v2/guides/transactions/transfer-routing).

| Transaction type                                                                                | Source Type                                                                 | Destination Type                                                                                                                                                                                              |
| ----------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| Deposit - [Cobo Loop](https://manuals.cobo.com/en/portal/custodial-wallets/cobo-loop) transfers | DepositFromLoop                                                             | DepositToAddress                                                                                                                                                                                              |
| Deposit - Transfers between Exchange Wallets                                                    | DepositFromWallet                                                           | DepositToWallet                                                                                                                                                                                               |
| Deposit - Other deposit transactions                                                            | DepositFromAddress                                                          | DepositToAddress                                                                                                                                                                                              |
| Withdrawal - Transfers between Exchange Wallets                                                 | Main<br />Sub                                                               | ExchangeWallet                                                                                                                                                                                                |
| Withdrawal - Other withdrawal transactions                                                      | Asset<br />Web3<br />Org-Controlled<br />User-Controlled<br />Main<br />Sub | Address                                                                                                                                                                                                       |
| ContractCall                                                                                    | Org-Controlled<br />User-Controlled<br />Web3                               | EVM\_Contract<br />SOL\_Contract<br />STELLAR\_Contract<br />TRON\_Contract                                                                                                                                   |
| MessageSign                                                                                     | Org-Controlled<br />User-Controlled<br />Web3                               | EVM\_EIP\_191\_Signature<br />EVM\_EIP\_712\_Signature<br />BTC\_BIP\_137\_Signature<br />BTC\_EIP\_191\_Signature<br />BTC\_BIP\_322\_Signature<br />COSMOS\_ADR\_36\_Signature<br />Raw\_Message\_Signature |
| Stake                                                                                           | Org-Controlled                                                              | Address                                                                                                                                                                                                       |
| Unstake                                                                                         | Org-Controlled                                                              | Address                                                                                                                                                                                                       |

## Transaction source types

The transaction source types are as follows:

* `Asset`: A Custodial Wallet (Asset Wallet).
* `Web3`: A Custodial Wallet (Web3 Wallet).
* `Org-Controlled`: An MPC Wallet (Organization-Controlled Wallet).
* `User-Controlled`: An MPC Wallet (User-Controlled Wallet).
* `Main`: An Exchange Wallet (Main Account).
* `Sub`: An Exchange Wallet (Sub Account).
* `DepositFromAddress`: A wallet address.
* `DepositFromWallet`: An Exchange Wallet.
* `DepositFromLoop`: A transfer sent through the [Cobo Loop](https://manuals.cobo.com/en/portal/custodial-wallets/cobo-loop) transfer network.

### `address` and `included_utxos` usage

This section explains, when the `source_type` is `Web3`, `Org-Controlled`, or `User-Controlled`, which `source` properties (`address` and `included_utxos`) need to be specified for different chains and transaction types, and how the system processes them.

#### UTXO-based chains

* **Regular transactions**
  * If only `included_utxos` is specified: The transaction will use only these specified UTXOs.
  * If only `address` is specified: The system will select UTXOs only from this address.
  * If both `address` and `included_utxos` are specified: The system will verify that the UTXOs belong to the specified address, and only these UTXOs will be used.
  * If neither `address` nor `included_utxos` is specified: The system will automatically select UTXOs from all addresses under the wallet associated with `wallet_id`.

* **RBF transactions**
  <br />`address` or `included_utxos` in an RBF transaction can be different from those in the original transaction.<br />
  * If only `included_utxos` is specified: The transaction will use only these specified UTXOs.
  * If only `address` is specified: The system will select UTXOs only from this address.
  * If both `address` and `included_utxos` are specified: The system will verify that the UTXOs belong to the specified address, and only these UTXOs will be used.
  * If neither `address` nor `included_utxos` is specified:
    * If the original transaction specified `included_utxos`: The transaction will use the UTXOs specified in the original transaction.
    * If the original transaction did not specify `included_utxos`: The system will automatically select UTXOs from all addresses under the wallet associated with `wallet_id` in the original transaction.

#### Account-based chains

* The transaction must specify `address`, otherwise the token transfer will fail.
* When estimating transfer fees, providing only `wallet_id` is sufficient; `address` is not required.

## Transaction destination types

The transaction destination types are as follows:

* `Address`: A wallet address.
* `ExchangeWallet`: An Exchange Wallet.
* `EVM_Contract`: An Ethereum Virtual Machine (EVM) smart contract.
* `SOL_Contract`: A Solana smart contract (program).
* `Stellar_Contract`: A Stellar smart contract.
* `TRON_Contract`: A TRON smart contract.
* `EVM_EIP_191_Signature`: An EVM EIP-191 signature. For more details, see [Signed Data Standard](https://eips.ethereum.org/EIPS/eip-191).
* `EVM_EIP_712_Signature`: An EVM EIP-712 signature. For more details, see [Typed structured data hashing and signing](https://eips.ethereum.org/EIPS/eip-712).
* `BTC_BIP_137_Signature`: A BTC BIP-137 signature. For more details, see [BIP-137](https://github.com/bitcoin/bips/blob/master/bip-0137.mediawiki).
* `BTC_EIP_191_Signature`: A BTC EIP-191 signature.
* `BTC_BIP_322_Signature`: A BTC BIP-322 signature. For more details, see [BIP-322](https://github.com/bitcoin/bips/blob/master/bip-0322.mediawiki).
* `COSMOS_ADR_36_Signature`: A COSMOS ADR-36 signature. For more details, see [ADR-36](https://github.com/cosmos/cosmos-sdk/blob/main/docs/architecture/adr-036-arbitrary-signature.md).
* `Raw_Message_Signature`: A raw message signature.
* `DepositToAddress`: A wallet address.
* `DepositToWallet`: An Exchange Wallet.


# Transaction statuses and sub-statuses
Source: https://cobo.com/developers/v2/guides/transactions/status

Guide to understanding transaction statuses in WaaS 2.0.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

WaaS 2.0 defines a range of transaction statuses and sub-statuses to reflect different processing stages. This page provides a complete list of statuses and describes the actions you can perform based on each status.

## Status reference table

### Deposits

The table below provides an overview of transaction statuses and sub-statuses relevant to deposits in the WaaS 2.0 service.

<table>
  <tr>
    <th>Status</th>
    <th>Sub-Status</th>
    <th>Description</th>
  </tr>

  <tr>
    <td>PendingScreening</td>
    <td>PendingScreeningAppCheck</td>
    <td>The transaction is under review by the [Screening app](https://manuals.cobo.com/en/apps/screening/introduction).</td>
  </tr>

  <tr>
    <td>PendingCoboKYTCheck</td>
    <td>The transaction is pending Cobo's KYT check.</td>
  </tr>

  <tr>
    <td>Confirming</td>
    <td>PendingBlockConfirmations</td>
    <td>The transaction is awaiting the required number of confirmations.</td>
  </tr>

  <tr>
    <td>Completed</td>
    <td>N/A</td>
    <td>The transaction is completed and funds are available.</td>
  </tr>

  <tr>
    <td>Rejected</td>
    <td>RejectedByCoboKYT</td>
    <td>The transaction was rejected by Cobo KYT.</td>
  </tr>

  <tr>
    <td>RejectedByScreeningApp</td>
    <td>The transaction was rejected by the Screening app.</td>
  </tr>
</table>

### Withdrawals

The table below provides an overview of transaction statuses and sub-statuses relevant to withdrawals in the WaaS 2.0 service.

<table>
  <tr>
    <th>Status</th>
    <th>Sub-Status</th>
    <th>Description</th>
  </tr>

  <tr>
    <td>Submitted</td>
    <td>N/A</td>
    <td>The transaction is submitted.</td>
  </tr>

  <tr>
    <td>PendingScreening</td>
    <td>PendingTravelRuleCheck</td>
    <td>The transaction is undergoing a Travel Rule check.</td>
  </tr>

  <tr>
    <td>PendingTravelRuleInfo</td>
    <td>The transaction is awaiting users to provide information related to the Travel Rule.</td>
  </tr>

  <tr>
    <td>PendingScreeningAppCheck</td>
    <td>The transaction is under review by the [Screening app](https://manuals.cobo.com/en/apps/screening/introduction).</td>
  </tr>

  <tr>
    <td>PendingCoboKYTCheck</td>
    <td>The transaction is pending Cobo's KYT check.</td>
  </tr>

  <tr>
    <td>PendingAuthorization</td>
    <td>PendingDoubleCheck</td>
    <td>The transaction is pending a double check.</td>
  </tr>

  <tr>
    <td>PendingSpenderCheck</td>
    <td>The transaction is pending a spender check.</td>
  </tr>

  <tr>
    <td>PendingRiskControlCheck</td>
    <td>The transaction is pending for a Risk Control check.</td>
  </tr>

  <tr>
    <td>PendingApproverCheck</td>
    <td>The transaction is pending approval from the approver.</td>
  </tr>

  <tr>
    <td>PendingCoboCheck</td>
    <td>The transaction is pending an internal check by Cobo.</td>
  </tr>

  <tr>
    <td>PendingSignature</td>
    <td>Queue</td>
    <td>The transaction is queued to be processed by Cobo Portal.</td>
  </tr>

  <tr>
    <td>PendingWaitSigner</td>
    <td>The transaction is waiting for a signer to sign it in Cobo Guard.</td>
  </tr>

  <tr>
    <td>InsufficientBalance</td>
    <td>The transaction cannot proceed due to insufficient balance. Please deposit required tokens or cancel the transaction.</td>
  </tr>

  <tr>
    <td>InsufficientBalanceFundLocked</td>
    <td>The transaction cannot proceed because the available balance is currently locked. Please wait until the balance is unlocked.</td>
  </tr>

  <tr>
    <td>PendingSystemProcessing</td>
    <td>The transaction has been submitted and is awaiting processing by the blockchain system.</td>
  </tr>

  <tr>
    <td>SystemProcessingOngoing</td>
    <td>The blockchain system is currently processing the transaction.</td>
  </tr>

  <tr>
    <td>Built</td>
    <td>The transaction has been built but not signed yet.</td>
  </tr>

  <tr>
    <td>PendingSignerApproval</td>
    <td>The transaction is pending approval from the signer.</td>
  </tr>

  <tr>
    <td>PendingApprovalStart</td>
    <td>The transaction approval is waiting to be started.<ul><li>For <a href="https://manuals.cobo.com/en/portal/mpc-wallets/ucw/introduction">MPC Wallets (User-Controlled Wallets)</a>, you need to use the Client App and call the UCW SDK to start the transaction approval process.</li><li>For <a href="https://manuals.cobo.com/en/portal/mpc-wallets/ocw/introduction">MPC Wallets (Organization-Controlled Wallets)</a>:<ul><li>If you are using the <a href="https://manuals.cobo.com/en/portal/mpc-wallets/ocw/create-key-share-groups">server co-signer</a>, this status indicates that the TSS Node will soon request the callback server to start the <a href="https://manuals.cobo.com/en/portal/risk-controls/introduction">risk controls</a> check. No further action is required from you at this stage.</li><li>If you are using the <a href="https://manuals.cobo.com/en/portal/mpc-wallets/ocw/create-key-share-groups">mobile co-signer</a>, key share holders need to use their <a href="https://manuals.cobo.com/en/guard/introduction">Cobo Guard</a> to approve the transaction and participate in the signing process.</li></ul></li></ul></td>
  </tr>

  <tr>
    <td>PendingSignerProcessing</td>
    <td>The transaction is currently being signed.</td>
  </tr>

  <tr>
    <td>SignatureVerificationSuccess</td>
    <td>The transaction's signature has been successfully verified.</td>
  </tr>

  <tr>
    <td>Broadcasting</td>
    <td>FailedBroadcasting</td>
    <td>The transaction failed to be broadcast to the blockchain network.</td>
  </tr>

  <tr>
    <td>Confirming</td>
    <td>Reverting</td>
    <td>The transaction is being reverted due to failure on the blockchain.</td>
  </tr>

  <tr>
    <td>PendingBlockConfirmations</td>
    <td> The transaction is awaiting the required number of confirmations.</td>
  </tr>

  <tr>
    <td>Completed</td>
    <td>N/A</td>
    <td>The transaction is completed.</td>
  </tr>

  <tr>
    <td>Failed</td>
    <td>FailedBySigner</td>
    <td>The transaction failed during the signing process.</td>
  </tr>

  <tr>
    <td>FailedOnChain</td>
    <td>The transaction failed on the blockchain.</td>
  </tr>

  <tr>
    <td>ReplacedByNewTransaction</td>
    <td>The transaction has been replaced by a new transaction through the Replace-By-Fee (RBF) mechanism.</td>
  </tr>

  <tr>
    <td>SignatureVerificationFailed</td>
    <td>The transaction's signature failed verification.</td>
  </tr>

  <tr>
    <td>FailedSignerTimeout</td>
    <td>The transaction failed due to signature timeout.</td>
  </tr>

  <tr>
    <td>ReOrged</td>
    <td>The transaction failed due to a blockchain reorganization.</td>
  </tr>

  <tr>
    <td>Rejected</td>
    <td>RejectedWhiteList</td>
    <td>The transaction was rejected because the IP address of the initiator was not in the whitelist.</td>
  </tr>

  <tr>
    <td>RejectedKYT</td>
    <td>The transaction was rejected because it failed Know Your Transaction (KYT) compliance checks.</td>
  </tr>

  <tr>
    <td>RejectedRiskControlCheck</td>
    <td>The transaction was rejected because it failed the risk control check.</td>
  </tr>

  <tr>
    <td>RejectedSpenderAuth</td>
    <td>The transaction was rejected by the spender.</td>
  </tr>

  <tr>
    <td>RejectedApproverAuth</td>
    <td>The transaction was rejected by the approver.</td>
  </tr>

  <tr>
    <td>RejectedDoubleCheck</td>
    <td>The transaction was rejected because it failed a double check.</td>
  </tr>

  <tr>
    <td>RejectedbyMobileCosigner</td>
    <td>The transaction was rejected by a mobile cosigner.</td>
  </tr>

  <tr>
    <td>RejectedCoboCheck</td>
    <td>The transaction was rejected because it failed the internal check by Cobo.</td>
  </tr>

  <tr>
    <td>RejectedByScreeningApp</td>
    <td>The transaction was rejected because it failed the screening check by the [Screening app](https://manuals.cobo.com/en/apps/screening/introduction).</td>
  </tr>

  <tr>
    <td>RejectedTravelRuleDueToUnsupportedToken</td>
    <td>The transaction was rejected because the token was not supported by the Travel Rule.</td>
  </tr>

  <tr>
    <td>RejectedTravelRule</td>
    <td>The transaction was rejected because it failed to comply with the Travel Rule.</td>
  </tr>

  <tr>
    <td>RejectedTravelRuleDueToCompliance</td>
    <td>The transaction was rejected because it failed the cross-check of the Travel Rule.</td>
  </tr>

  <tr>
    <td>RejectedTransactionPolicy</td>
    <td>The transaction was rejected due to it failed the transaction policies.</td>
  </tr>

  <tr>
    <td>RejectedBySigner</td>
    <td>The transaction was rejected by the signer.</td>
  </tr>

  <tr>
    <td>CanceledBySpender</td>
    <td>The transaction was canceled by a spender.</td>
  </tr>

  <tr>
    <td>CanceledByAPI</td>
    <td>The transaction was canceled by a [Cancel transaction](https://www.cobo.com/developers/v2/api-references/transactions/cancel-transaction) operation.</td>
  </tr>

  <tr>
    <td>OnchainRejection</td>
    <td>The transaction was rejected from being added to the blockchain.</td>
  </tr>

  <tr>
    <td>RejectedByCobo</td>
    <td>The transaction was rejected by Cobo possibly due to unmet compliance or risk control requirements. You can contact our [support team](mailto:help@cobo.com) for more details.</td>
  </tr>

  <tr>
    <td>Pending</td>
    <td>N/A</td>
    <td>The transaction is waiting to be included in a block.</td>
  </tr>
</table>

## Status details

<Note>
  The `PendingAuthorization` status aggregates both manual approval steps and internal automated checks. Manual steps include `PendingApproverCheck`, `PendingSpenderCheck`, and `PendingDoubleCheck`. Automated checks include `PendingRiskControlCheck` and `PendingCoboCheck`. A transaction in `PendingAuthorization` does not necessarily require a person to act, because it may be undergoing automated risk-control or compliance checks.
</Note>

<Warning>
  After a transaction is approved, it enters the `PendingSignature` status and must be signed by the MPC signer group within a limited signing window. If signing does not complete within this window, the transaction automatically fails and moves to the `Failed` status with the sub-status `FailedSignerTimeout`. To find out why a transaction failed, check the `sub_status` field returned by [List all transactions](/developers/v2/api-references/transactions/list-all-transactions) or [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information). If you encounter `FailedSignerTimeout`, the transaction is in a terminal `Failed` state and cannot be resumed. Submit a new transaction of the same type to try again: use [Transfer token](/developers/v2/api-references/transactions/transfer-token) for token transfers, [Call smart contract](/developers/v2/api-references/transactions/call-smart-contract) for contract calls, or [Sign message](/developers/v2/api-references/transactions/sign-message) for message signing.
</Warning>

<Note>
  A transaction in the `Confirming` status with the sub-status `PendingBlockConfirmations` is waiting for the required number of block confirmations on its chain. This is a normal part of processing and does not mean the transaction is stuck. The required number of confirmations and the expected confirmation time vary by chain.
</Note>

## Available actions

You can perform the following actions based on the transaction status:

* Cancel a transaction if its status is one of the following:
  * `Submitted`
  * `PendingScreening`
  * `PendingAuthorization`
  * `PendingSignature` (Only when the sub-status is `Queue`, `InsufficientBalance`, `InsufficientBalanceFundLocked`, `PendingSignerApproval`, `PendingSystemProcessing`, or `Built`)
* Resend a transaction if its status is `Failed`.
* Speed up or drop a transaction if its status is `Broadcasting`.

For details on how a replaced transaction's status changes, see [RBF (Replace-By-Fee) transaction lifecycle](/developers/v2/guides/transactions/rbf-transaction-lifecycle).

For more details, refer to [Manage transactions](/developers/v2/guides/transactions/manage-transactions).


# Transaction status flow for Custodial Wallets (Asset Wallets)
Source: https://cobo.com/developers/v2/guides/transactions/transaction-process-custodial

Understand the detailed transaction status flow for deposits and withdrawals in Custodial Wallets (Asset Wallets)

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This article explains how deposit and withdrawal transactions are processed for Custodial Wallets (Asset Wallets). It outlines the steps taken by you and Cobo, along with the various transaction statuses and sub-statuses your transaction might go through. You can call [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) to query the current status and sub-status of your transaction.

## Deposit process

The following diagram illustrates how a deposit into your Custodial Wallet (Asset Wallet) is processed:

<img alt="Deposit process" />

* Cobo reserves the right to reject a deposit transaction if it violates compliance regulations. If rejected, the deposit will not appear on Cobo Portal or trigger any webhook events.
* If the transaction amount is below the minimum deposit threshold, the transaction will not be processed and no record will be created. You can call the [Get token information](/developers/v2/api-references/wallets/get-token-information) operation to retrieve the minimum deposit amount for each token type.

## Withdrawal process

The following diagram illustrates how a withdrawal from your Custodial Wallet (Asset Wallet) is processed:

<img alt="Withdrawal process" />

* If a withdrawal is rejected or unsuccessful, the tokens will be returned to your wallet, and your balance will remain unchanged.
* If your withdrawal amount is smaller than the minimum withdrawal threshold, the withdrawal request will receive an error. You can call the [Get token information](/developers/v2/api-references/wallets/get-token-information) operation to retrieve the minimum withdrawal amount for each token type.


# Transaction status flow for MPC Wallets and Web3 Wallets
Source: https://cobo.com/developers/v2/guides/transactions/transaction-process-mpc

Understand the detailed transaction status flow for deposits and withdrawals in MPC Wallets and Custodial Wallets (Web3 Wallets)

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This article explains how deposit and withdrawal transactions are processed for MPC Wallets and Custodial Wallets (Web3 Wallets). It outlines the steps taken by you and Cobo, along with the various transaction statuses and sub-statuses your transaction might go through. You can refer to [Statuses and Sub-Statuses](/developers/v2/guides/transactions/status) for a comprehensive list of statuses and sub-statuses, or call [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information) to query the current status and sub-status of your transaction.

## Deposit process

The following diagram illustrates how a deposit is processed:

<img alt="Deposit process" />

* Cobo reserves the right to reject a deposit transaction if it violates compliance regulations.
* If the transaction amount is below the minimum deposit threshold, the transaction will not be processed and no record will be created. You can call the [Get token information](/developers/v2/api-references/wallets/get-token-information) operation to retrieve the minimum deposit amount for each token type.

## Withdrawal process

The following diagram illustrates how a withdrawal is processed. Colors are used to indicate different status types:

* Yellow: User action is required for the transaction to proceed
* Green: Completed successfully
* Red: Unsuccessful, including failed or rejected statuses

<Note>Sub-states on the left without connecting arrows are optional and occur only under specific conditions.</Note>

<Info>For better visibility, open the image in a new tab.</Info>

<img alt="Withdrawal process" />

* If a withdrawal is rejected or unsuccessful, the tokens will be returned to your wallet, and your balance will remain unchanged.
* If your withdrawal amount is smaller than the minimum withdrawal threshold, the withdrawal request will receive an error. You can call the [Get token information](/developers/v2/api-references/wallets/get-token-information) operation to retrieve the minimum withdrawal amount for each token type.

<Warning>
  After a withdrawal is approved, it enters the `PendingSignature` status and must be signed by the MPC signer group within a limited signing window. If signing does not complete in time, the transaction automatically fails and moves to the `Failed` status with the sub-status `FailedSignerTimeout`. To confirm the reason, check the `sub_status` field returned by [Get transaction information](/developers/v2/api-references/transactions/get-transaction-information). Because `FailedSignerTimeout` is a terminal `Failed` state, submit a new transaction to try again — for example, initiate a new transfer with the [Transfer token](/developers/v2/api-references/transactions/transfer-token) operation.
</Warning>


# Transfer routing
Source: https://cobo.com/developers/v2/guides/transactions/transfer-routing

Understand how token transfers are processed as Cobo Loop transfers or on-chain transfers, and how to control that behavior with request parameters.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## Overview

Every token transfer is processed in one of the following ways:

* **Cobo Loop transfer** settles off-chain between accounts on Cobo Portal through the Cobo Loop transfer network, when the destination supports it.
* **On-chain transfer** broadcasts the transaction to the blockchain.

## Control routing with request parameters

The [Transfer token](/developers/v2/api-references/transactions/transfer-token) operation provides two boolean parameters to control whether the transfer uses Cobo Loop or is sent on-chain: `force_internal` and `force_external`.

| Setting                   | Routing behavior                                                                       |
| ------------------------- | -------------------------------------------------------------------------------------- |
| `force_internal` = `true` | Forces the transfer to use Cobo Loop (off-chain).                                      |
| `force_external` = `true` | Forces the transfer to be sent on-chain.                                               |
| Both `false` (default)    | Uses Cobo Loop if the destination supports it; otherwise sends the transfer on-chain.  |
| Both `true`               | The request is rejected with an HTTP 400 error (error code `2006`, invalid parameter). |

These parameters are available only for transfers to an address destination. For the supported destination types, see the [Transfer token](/developers/v2/api-references/transactions/transfer-token) operation.

## Related guides

* [Transaction sources and destinations](/developers/v2/guides/transactions/sources-and-destinations)
* [Cobo Loop](https://manuals.cobo.com/en/portal/custodial-wallets/cobo-loop)


# Validate addresses
Source: https://cobo.com/developers/v2/guides/transactions/validate-addresses

Validate transaction destination addresses server-side with the Cobo API instead of hand-coded, per-chain format rules.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Validating an address before you use it as a transaction destination helps you avoid failed transactions and funds sent to malformed addresses. The canonical way to validate an address is to call the Cobo API, which performs the check server-side for the specified chain. Do not rely on hand-coded, per-chain address-format rules in your own integration, because address formats differ by chain and change over time.

## Validate a single address (WaaS 2.0)

Use the [Check address validity](/developers/v2/api-references/wallets/check-address-validity) operation (`GET /wallets/check_address_validity`). Pass two query parameters: `chain_id` (the chain to validate against) and `address` (the address to check). The response contains a single boolean field, `validity`: `true` means the address is valid for that chain, and `false` means it is not. The response is a boolean only and does not include a reason field.

Worked example — validating an XRP address: pass `chain_id` set to `XRP` and `address` set to the address you want to check. Because validation is performed server-side per `chain_id`, the same address is judged against the rules of the chain you specify.

## Validate multiple addresses (WaaS 2.0)

Two batch operations are available:

* [Check addresses validity](/developers/v2/api-references/wallets/check-addresses-validity) (`GET /wallets/check_addresses_validity`): validates multiple addresses for a single chain in one request.
* [Check address validity across chains](/developers/v2/api-references/wallets/check-address-validity-across-chains) (`GET /wallets/check_address_chains_validity`): validates one address across multiple chains in one request.

## Validate an address (WaaS 1.0)

If you are still on WaaS 1.0, use the equivalent legacy operations:

* [GET /v1/custody/is\_valid\_address/](/developers/v1/api-references/custody-wallet/is_valid_address) for Custodial Wallets.
* [GET /v1/custody/mpc/is\_valid\_address/](/developers/v1/api-references/mpc-wallet/mpc_is_valid_address) for MPC Wallets.

It is recommended to migrate to WaaS 2.0 and use Check address validity.

## Related guides

* [List all transactions](/developers/v2/api-references/transactions/list-all-transactions)
* [Check address validity](/developers/v2/api-references/wallets/check-address-validity)


# Introduction to Webhooks and Callbacks
Source: https://cobo.com/developers/v2/guides/webhooks-callbacks/introduction

Introduction to webhooks and callbacks in WaaS 2.0, explaining their purpose and implementation.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Webhooks and callbacks are essential mechanisms for the WaaS service to communicate with your application. After you set up and register callback and webhook endpoints, the WaaS service sends push messages to the designated URL when an event occurs. They allow your application to receive real-time updates or notifications and to respond to events accordingly.

## Webhooks vs callbacks

Callbacks and webhooks serve distinct purposes within your business operations.

| Mechanism | Description                                                                                                                       | Trigger Condition                                                                                                                              | Required Actions Upon Receiving the Message                                                                                                                                               |
| --------- | --------------------------------------------------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| Callbacks | Serve similarly to a 2FA verification. You must register a callback endpoint in order to approve and complete a token withdrawal. | Triggered when you initiate a withdrawal or contract call using the WaaS API.                                                                  | Check if the transaction meets expectations, and respond with a success status code (`200` or `201`) and a response body of `ok` or `deny` to indicate transaction approval or rejection. |
| Webhooks  | Serve as real-time notifications for events such as transaction status updates.                                                   | Triggered when certain events occur such as transaction status or TSS request status changes, based on the event types to which you subscribe. | Respond with a success status code (`200` or `201`).                                                                                                                                      |

You can view the data of all webhook events and callback messages in your organization on **Cobo Portal** > **Developer**> **Webhook Events** / **Callback Messages**.

## Handle webhook events and callback messages

Follow the steps listed below to handle webhook events and callback messages sent from the WaaS service:

1. Create a webhook or callback endpoint.
   * Choose a server environment.
   * Define an endpoint URL.
2. Implement the handling logic on the server side.
   * Parse the API request.
   * Verify the signature.
   * Respond to the API request.
   * Add other handling logic (if applicable).
3. Register the endpoint on Cobo Portal.
   <Note>When registering a webhook endpoint, you need to specify the event types to which you want to subscribe.</Note>

To create an endpoint and implement the handling logic, see [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).

To register the endpoint, see [Register a webhook endpoint](https://manuals.cobo.com/en/portal/developer-console/webhooks-create) and [Register a callback endpoint](https://manuals.cobo.com/en/portal/developer-console/callbacks-register).

To learn more about event types and event data types, see [Webhook event type and data type](/developers/v2/guides/webhooks-callbacks/webhook-event-type).

To manage webhook events using Cobo CLI, refer to the following guides: [Listen and Forward Events](/developers/v2/developer-tools/cobo-cli/listen-and-forward-events), [Trigger Webhook Events](/developers/v2/developer-tools/cobo-cli/trigger-events), and [List Event Types](/developers/v2/developer-tools/cobo-cli/event-types).

## Notes on upgrading from WaaS 1.0 to Waas 2.0

The WaaS 1.0 service uses API callbacks for transaction notifications and withdrawal confirmations, similar to the webhooks and callbacks introduced in WaaS 2.0. The following table provides a comparison between the two versions based on the event notification mechanisms:

|          | Mechanism to Notify Transaction Status Changes | Mechanism to Confirm Withdrawals     | Where to Register the Endpoint |
| -------- | ---------------------------------------------- | ------------------------------------ | ------------------------------ |
| WaaS 1.0 | Callbacks - Transaction notifications          | Callbacks - Withdrawal confirmations | Cobo Custody                   |
| WaaS 2.0 | Webhook events                                 | Callback messages                    | Cobo Portal                    |

For more details about the WaaS 1.0 callbacks, refer to [How to Configure API Callback](/developers/v1/guides/howtos/configure-api-callback).

### Continued use of the WaaS 1.0 API

If you choose to continue using the WaaS 1.0 API, no additional configuration is required. The existing API callbacks will function as expected.

### Upgrade to the WaaS 2.0 API

When upgrading to WaaS 2.0, you need to do the following:

* Set up your webhook or callback endpoint by following the instructions in [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).
* Register the endpoint on the Cobo Portal by following the instructions in [Register a webhook endpoint](https://manuals.cobo.com/en/portal/developer-console/webhooks-create) or [Register a callback endpoint](https://manuals.cobo.com/en/portal/developer-console/callbacks-register).

<Note>The WaaS 1.0 API callbacks use a different signature algorithm compared to the WaaS 2.0 webhooks and callbacks. Do not directly register your WaaS 1.0 endpoint on Cobo Portal. Otherwise, your endpoint will receive errors due to the differences in the signature algorithm and webhook/callback data structure between WaaS 1.0 and WaaS 2.0. Ensure you refer to the [sample code](/developers/v2/guides/webhooks-callbacks/set-up-endpoint#code-samples) provided to correctly configure your endpoint for WaaS 2.0.</Note>

<Note><p>If you configure WaaS 1.0 API callbacks for transaction notifications but do not set up WaaS 2.0 webhooks, your endpoint will still receive transaction notifications from WaaS 1.0.</p>If you configure both WaaS 1.0 API callbacks for transaction notifications and WaaS 2.0 webhooks, while continuing to use the WaaS 1.0 API, your endpoint will receive:<ul><li>From WaaS 1.0: Transaction notifications.</li><li>From WaaS 2.0: Webhook events.</li></ul>In this case, you need to implement deduplication using a unique ID (such as `cobo_id`) to avoid processing duplicate notifications.</Note>


# Set up a callback or webhook endpoint
Source: https://cobo.com/developers/v2/guides/webhooks-callbacks/set-up-endpoint

Step-by-step guide to setting up a webhook endpoint in WaaS 2.0 for real-time event notifications.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Webhook events and callback messages are crucial for ensuring seamless data integration and communication between the WaaS service and your application. This guide provides an overview of how to create and manage an endpoint for receiving and processing webhook events and callback messages.

## Create an endpoint

First, choose a server environment, such as a cloud service like AWS, Google Cloud, or a self-hosted server, that supports receiving and processing webhook events or callback messages. Then, define an endpoint URL on your server where the webhook events and callback messages will be sent.

## Implement handling logic

After you create the endpoint, you need to implement the logic on the server to handle the webhook events or callback messages, including parsing the API request, verifying the signature, responding to the request and adding other handling logic if necessary.

### Verify the signature

To prevent unauthorized access, when you receive a webhook event or a callback message, you need to validate the authenticity of the API request by verifying the signature.

<Warning>
  The Ed25519 signature is computed over the exact raw bytes of the HTTP request body. You must verify the signature against the raw body exactly as you received it. Do not parse the JSON and then re-serialize it before verifying — re-encoding can strip `null` or empty fields and reorder keys, which changes the bytes and causes signature verification to fail. Always build the message as `raw_body|timestamp` using the unmodified raw body.
</Warning>

The verification steps are as follows:

1. Retrieve raw body and timestamp.

   Extract the original body string from the request payload and the timestamp from the request headers.

   ```python theme={null}
   raw_body = request.body().decode('utf8')
   timestamp = request.headers.get("BIZ_TIMESTAMP")
   ```

2. Retrieve the signature.

   Fetch the signature value from the request header.

   ```python theme={null}
   signature = request.headers.get('BIZ_RESP_SIGNATURE')
   ```

3. Concatenate and hash the message.

   ```python theme={null}
   import hashlib

   # Concatenate raw body and timestamp to form the message.
   message = "raw_body|timestamp"

   # Compute double SHA-256 hash.
   sha256_hash = hashlib.sha256(hashlib.sha256(message.encode()).digest()).digest()
   ```

4. Select Cobo's Public Key.

   Depending on the environment that you use, select the corresponding public key for verification:

   * Development environment: `a04ea1d5fa8da71f1dcfccf972b9c4eba0a2d8aba1f6da26f49977b08a0d2718`
   * Production environment: `8d4a482641adb2a34b726f05827dba9a9653e5857469b8749052bf4458a86729`

5. Verify the signature using the Ed25519 algorithm.

   ```python theme={null}
   import ed25519

   # Obtain the verifying key from Cobo's public key.
   vk = ed25519.VerifyingKey(bytes.fromhex(public_key)) 

   # Verify the signature against the computed message hash.
   vk.verify(bytes.fromhex(signature), sha256_hash)
   ```

### Respond to the API request

Properly responding to webhook events and callback messages is crucial for ensuring that webhooks and callbacks are processed as expected. This section describes the expected response from both webhook and callback endpoints.

#### Webhook events

When your webhook endpoint receives a webhook event, it should respond with a status code of `200` or `201` to indicate that the event has been successfully received and processed. Once this response is sent, the WaaS service will stop retrying to send the event and the event status will become `Delivered` on Cobo Portal.

The default timeout for each webhook event is 2 seconds. If the webhook endpoint does not respond or responds with a status code other than `200` or `201`, the WaaS service will continue to retry sending the event. If the number of retry attempts reaches 10 , the WaaS service will stop sending the event and the event status will become `Failed`· You can resend the event by clicking **Retry** on **Cobo Portal** > **Developer** > **WaaS 2.0** > **Webhook Events**.

Cobo does not guarantee that events will be delivered in the order they are generated. For example, creating a transfer will generate the following events:

* `wallets.transaction.created`
* `wallets.transaction.updated`
* `wallets.transaction.succeeded`

Your endpoint should not assume that events will arrive in this sequence and must handle delivery appropriately.

#### Callback messages

When your callback endpoint receives a callback message, it should respond with a status code of `200` or `201` and a response body of `ok` or `deny` to indicate transaction approval or rejection. Once this response is sent, the WaaS service will stop retrying to send the message and the callback message status will become `Delivered`on Cobo Portal.

If the callback endpoint does not respond, responds with a status code other than `200` or `201`,  or the response body does not contain `ok` or `deny`, the WaaS service will continue to retry sending the message.  If the number of retry attempts reaches 30, the WaaS service will stop sending the message and the callback message status will become `Failed`. You can resend the message by using the [Retry callback message](/developers/v2/api-references/developers/retry-callback-message) operation.

### Common delivery failures

The following table lists the most frequent reasons why callback messages or webhook events fail to deliver, and how to fix them.

| Symptom                                                                                                                    | Root cause                                                                          | Fix                                                                                                                                                                               |
| -------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| Callback message status is `Retrying` or `Failed`; response body in the Portal log shows `{"result":"ok"}` or similar JSON | Response body is JSON instead of plain text                                         | Change your response body to the exact string `ok` or `deny` — no JSON wrapping, no quotes.                                                                                       |
| Callback message shows no delivery attempts for a new URL                                                                  | Endpoint not publicly reachable (e.g. ngrok tunnel is not running or has restarted) | Start or restart your ngrok tunnel and verify the URL is reachable from outside your local network before registering.                                                            |
| Webhook events show `status_code: 301` or `302` in delivery logs                                                           | Server returned a redirect                                                          | Serve the response directly from the registered URL. Cobo does not follow redirects.                                                                                              |
| Delivery attempts fail with TLS or SSL error                                                                               | Endpoint TLS certificate is invalid or expired                                      | Renew the certificate on your server. The endpoint must use HTTPS with a valid certificate.                                                                                       |
| Events or messages stop arriving after a period                                                                            | Retry limit exhausted                                                               | Webhook events retry up to 10 times; callback messages retry up to 30 times. After the limit is reached, status becomes `Failed`. Manually retry from Cobo Portal or via the API. |

<Note>
  You can inspect the detailed response body and status code for each delivery attempt in Cobo Portal under **Developer** > **Webhook Events** / **Callback Messages** > click an event or message > **Delivery logs**.
</Note>

### Code samples

To see examples of how to implement the handling logic, refer to the following files in the WaaS SDK GitHub repository:

* Python: [server\_demo.py](https://github.com/CoboGlobal/cobo-waas2-python-sdk/blob/master/cobo_waas2/server_demo.py) (implemented based on the FastAPI framework)
* Java: [DemoController.java](https://github.com/CoboGlobal/cobo-waas2-java-sdk/blob/master/src/main/java/com/cobo/waas2/demo/DemoController.java) (implemented based on the SpringBoot framework)
* JavaScript: [ServerDemo.js](https://github.com/CoboGlobal/cobo-waas2-js-sdk/blob/master/src/ServerDemo.js)
* Go: [server\_demo.go](https://github.com/CoboGlobal/cobo-waas2-go-sdk/blob/master/cobo_waas2/demo/server_demo.go)

## Advanced usage

### Wallet-level webhook routing

In certain business scenarios, you may need to apply different Webhook handling logic for different wallets. For example:

* Multiple business teams share the same WaaS account
* A single system manages multiple independent projects
* Webhook events need to be forwarded to different microservices

In such cases, you can route incoming Webhook events based on the `wallet_id`.
The following example demonstrates how to extend the Cobo-provided Webhook/Callback sample code ([server\_demo.py](https://github.com/CoboGlobal/cobo-waas2-python-sdk/blob/master/cobo_waas2/server_demo.py)) to implement wallet-level Webhook routing.

This example uses Python for demonstration, but the same logic can be applied to other languages. You may adapt this approach in the sample code of the language you are using.

```python theme={null}
@app.post("/api/webhook")
async def handle_webhook(
    request: Request,
    biz_timestamp: Optional[str] = Header(None),
    biz_resp_signature: Optional[str] = Header(None),
):
    raw_body = await request.body()
    sig_valid = verify_signature(
        pubkey,
        biz_resp_signature,
        f"{raw_body.decode('utf8')}|{biz_timestamp}"
    )
    if not sig_valid:
        raise HTTPException(status_code=401, detail="Signature verification failed")

    import requests
    event = WebhookEvent.from_dict(json.loads(raw_body.decode('utf8')))
    data = event.data.actual_instance

    # Route Webhook events based on Wallet ID
    # Replace "wallet_id_xxx" and the target URLs with your actual wallet IDs
    # and the corresponding Webhook endpoints in your own system.
    if data.data_type == "Transaction":
        if data.wallet_id == "wallet_id_1":
            # Example: Forward events for wallet_id_1 to Service A
            requests.post("http://wallet1.example.com/webhook", json=data.model_dump())

        elif data.wallet_id == "wallet_id_2":
            # Example: Forward events for wallet_id_2 to Service B
            requests.post("http://wallet2.example.com/webhook", json=data.model_dump())

        elif data.wallet_id == "wallet_id_3":
            # Example: Forward events for wallet_id_3 to Service C
            requests.post("http://wallet3.example.com/webhook", json=data.model_dump())

        else:
            # Default handling logic (optional)
            pass

    logger.info(event)
    logger.info(event.data)
```

## ⚠️⚠️⚠️Important notes

<Warning>
  * When receiving the webhook events, your endpoint should first return the correct status code promptly and then handle any subsequent processing asynchronously to prevent timeouts.
  * Due to the retry mechanism of webhook events, webhook endpoints may sometimes receive the same event multiple times. To protect against duplicate event processing, please log the event IDs, transaction hashes, or transaction IDs you've already processed and refrain from processing those that are already logged.
</Warning>


# Webhook event types and data types
Source: https://cobo.com/developers/v2/guides/webhooks-callbacks/webhook-event-type

Comprehensive list of webhook event types in WaaS 2.0, detailing each event's purpose and data structure.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## Webhook event types

<Info>Here, transaction refers to all types of transactions, including deposits, withdrawals, contract calls, and message signing.</Info>

### Payment events

For payment webhook events, please refer to [Order Status and Events](/developers/v2/payments/status-and-events).

### Transaction events (deposits/withdrawals/contract calls/message signing)

<Note>The following events apply to all types of transactions, including deposits, withdrawals, contract calls, and message signing.</Note>

<table>
  <thead>
    <tr>
      <th>Event Type</th>
      <th>Event Data Type</th>
      <th>When It Occurs</th>
    </tr>
  </thead>

  <tbody>
    <tr>
      <td><code>wallets.transaction.created</code></td>
      <td><code>Transaction</code></td>
      <td>A transaction has been detected on the blockchain, generating a transaction record. This event does not indicate that the transaction was successful.</td>
    </tr>

    <tr>
      <td><code>wallets.transaction.updated</code></td>
      <td><code>Transaction</code></td>
      <td>There are changes to a transaction's status or confirmation numbers.<Note>The <code>wallets.transaction.updated</code> event covers the entire lifecycle of a transaction, including creation, completion, and failure. If you want to track every status change, you need only subscribe to this event.</Note></td>
    </tr>

    <tr>
      <td><code>wallets.transaction.succeeded</code></td>
      <td><code>Transaction</code></td>
      <td>A transaction has been successfully completed.</td>
    </tr>

    <tr>
      <td><code>wallets.transaction.failed</code></td>
      <td><code>Transaction</code></td>
      <td>A transaction failed.</td>
    </tr>

    <tr>
      <td><code>token.suspended.deposit</code></td>
      <td><code>SuspendedToken</code></td>
      <td>A token deposit has been suspended.</td>
    </tr>

    <tr>
      <td><code>token.suspended.withdraw</code></td>
      <td><code>SuspendedToken</code></td>
      <td>A token withdrawal has been suspended.</td>
    </tr>
  </tbody>
</table>

### Fee Station events

<table>
  <thead>
    <tr>
      <th>Event Type</th>
      <th>Event Data Type</th>
      <th>When It Occurs</th>
    </tr>
  </thead>

  <tbody>
    <tr>
      <td><code>fee\_station.transaction.created</code></td>
      <td><code>Transaction</code></td>
      <td>A Fee Station transaction has been created.</td>
    </tr>

    <tr>
      <td><code>fee\_station.transaction.updated</code></td>
      <td><code>Transaction</code></td>
      <td>There are changes to the status of a Fee Station transaction.</td>
    </tr>

    <tr>
      <td><code>fee\_station.transaction.failed</code></td>
      <td><code>Transaction</code></td>
      <td>A Fee Station transaction failed.</td>
    </tr>

    <tr>
      <td><code>fee\_station.transaction.succeeded</code></td>
      <td><code>Transaction</code></td>
      <td>A Fee Station transaction has been successfully completed.</td>
    </tr>
  </tbody>
</table>

### MPC TSS request events

<table>
  <thead>
    <tr>
      <th>Event Type</th>
      <th>Event Data Type</th>
      <th>When It Occurs</th>
    </tr>
  </thead>

  <tbody>
    <tr>
      <td><code>wallets.mpc.tss\_request.created</code></td>
      <td><code>TSSRequest</code></td>
      <td>A TSS request is created.</td>
    </tr>

    <tr>
      <td><code>wallets.mpc.tss\_request.updated</code></td>
      <td><code>TSSRequest</code></td>
      <td>There are changes to the status of a TSS request.</td>
    </tr>

    <tr>
      <td><code>wallets.mpc.tss\_request.succeeded</code></td>
      <td><code>TSSRequest</code></td>
      <td>The requested action has been successfully completed.</td>
    </tr>

    <tr>
      <td><code>wallets.mpc.tss\_request.failed</code></td>
      <td><code>TSSRequest</code></td>
      <td>The requested action failed.</td>
    </tr>
  </tbody>
</table>

### Wallet and address management events

<table>
  <thead>
    <tr>
      <th>Event Type</th>
      <th>Event Data Type</th>
      <th>When It Occurs</th>
    </tr>
  </thead>

  <tbody>
    <tr>
      <td><code>wallets.addresses.created</code></td>
      <td><code>Addresses</code></td>
      <td>A new wallet address has been created.</td>
    </tr>

    <tr>
      <td><code>wallets.created</code></td>
      <td><code>WalletInfo</code></td>
      <td>A new wallet has been created.</td>
    </tr>

    <tr>
      <td><code>mpc\_vaults.created</code></td>
      <td><code>MPCVault</code></td>
      <td>A new MPC vault has been created.</td>
    </tr>
  </tbody>
</table>

<Note>Activating a Solana token sub-address (Associated Token Account) does not emit a `wallets.addresses.created` event. The rent transfer that funds the activation does not emit any `wallets.transaction.*` event and does not produce a deposit or transaction record. As a result, Solana token account activation and its rent are not visible through webhooks. For details, see [Solana token account rent](/developers/v2/guides/transactions/solana-token-account-rent).</Note>

### Token and chain management events

<table>
  <thead>
    <tr>
      <th>Event Type</th>
      <th>Event Data Type</th>
      <th>When It Occurs</th>
    </tr>
  </thead>

  <tbody>
    <tr>
      <td><code>wallet.token.enabled</code></td>
      <td><code>Tokens</code></td>
      <td>One or more tokens have been enabled.</td>
    </tr>

    <tr>
      <td><code>wallet.token.disabled</code></td>
      <td><code>Tokens</code></td>
      <td>One or more tokens have been disabled.</td>
    </tr>

    <tr>
      <td><code>wallet.chain.enabled</code></td>
      <td><code>Chains</code></td>
      <td>One or more chains have been enabled.</td>
    </tr>

    <tr>
      <td><code>wallet.chain.disabled</code></td>
      <td><code>Chains</code></td>
      <td>One or more chains have been disabled.</td>
    </tr>

    <tr>
      <td><code>wallets.token\_listing.failed</code></td>
      <td><code>TokenListing</code></td>
      <td>A token listing request failed.</td>
    </tr>

    <tr>
      <td><code>wallets.token\_listing.succeeded</code></td>
      <td><code>TokenListing</code></td>
      <td>A token listing request has been successfully processed and the token is now available.</td>
    </tr>
  </tbody>
</table>

### Balance update events

<table>
  <thead>
    <tr>
      <th>Event Type</th>
      <th>Event Data Type</th>
      <th>When It Occurs</th>
    </tr>
  </thead>

  <tbody>
    <tr>
      <td><code>wallet.mpc.balance.updated</code></td>
      <td><code>BalanceUpdateInfo</code></td>
      <td>The balance of an MPC Wallet has been updated.</td>
    </tr>

    <tr>
      <td><code>wallet.web3.balance.updated</code></td>
      <td><code>BalanceUpdateInfo</code></td>
      <td>The balance of a Custodial Wallet (Web3 Wallet) has been updated.</td>
    </tr>
  </tbody>
</table>

### Compliance events

<table>
  <thead>
    <tr>
      <th>Event Type</th>
      <th>Event Data Type</th>
      <th>When It Occurs</th>
    </tr>
  </thead>

  <tbody>
    <tr>
      <td><code>compliance.disposition.status.updated</code></td>
      <td><code>ComplianceDisposition</code></td>
      <td>There are changes to the status of a compliance disposition.</td>
    </tr>

    <tr>
      <td><code>compliance.kyt.screenings.status.updated</code></td>
      <td><code>ComplianceKytScreenings</code></td>
      <td>There are changes to the status of a KYT screening case.</td>
    </tr>
  </tbody>
</table>

### `ComplianceKytScreenings` event data

The `compliance.kyt.screenings.status.updated` event carries a `ComplianceKytScreenings` payload (`KytScreeningsEventData`). This payload reports two independent status fields, `review_status` and `funds_status`. Track them separately: `review_status` reflects the screening and review progress of the case, and `funds_status` reflects the state of the associated funds.

**`review_status` (`ReviewStatusType`)**

| Value              | Meaning                                                                          |
| ------------------ | -------------------------------------------------------------------------------- |
| `PendingScreening` | The screening case has been created and is waiting for AML/KYT screening to run. |
| `Screened`         | AML/KYT screening has completed for the case.                                    |
| `PendingDecision`  | Screening has completed and the case is awaiting a decision.                     |
| `PendingReview`    | The case requires manual review before a decision is reached.                    |
| `Approved`         | The case has been approved.                                                      |
| `Rejected`         | The case has been rejected.                                                      |
| `Unsupported`      | The case involves a chain or token that screening does not support.              |
| `Bypassed`         | Screening was skipped for the case.                                              |

**`funds_status` (`FundsStatusType`)**

| Value              | Meaning                                                            |
| ------------------ | ------------------------------------------------------------------ |
| `Frozen`           | The associated funds have been frozen.                             |
| `Refunding`        | A refund of the funds is in progress.                              |
| `Refunded`         | The funds have been refunded.                                      |
| `RefundFailed`     | The refund attempt failed.                                         |
| `Unfreezing`       | The funds are being unfrozen.                                      |
| `Unfrozen`         | The funds have been unfrozen.                                      |
| `UnfreezingFailed` | The attempt to unfreeze the funds failed.                          |
| `Isolating`        | The funds are being isolated.                                      |
| `Isolated`         | The funds have been isolated.                                      |
| `IsolationFailed`  | The attempt to isolate the funds failed.                           |
| `CoboDisposition`  | The funds are being handled through a Cobo disposition.            |
| `Normal`           | The funds are in a normal state with no compliance action applied. |

The case decision that drives these status changes is represented by `KytScreeningsDecisionsType`, which has the values `Approval`, `ApprovalWithAlert`, `Rejection`, and `ManualReview`.

## Data structure of webhook events

For a complete introduction of the webhook event data and its data structure, refer to the [data](/developers/v2/api-references/developers--webhooks/retrieve-event-information#response-data) property in the response of the Retrieve event information operation or the [data.data](/developers/v2/api-references/developers--webhooks/list-all-webhook-events#response-data-data) property in the response of the List all webhook event operation.

<img alt="Screenshot of the data property" />

Switch between the event data types to view the data structure of each event data type.

Additionally, you can view all webhook events in your organization on **Cobo Portal** > **Developer**> **Webhook Events**.


# Create Address Book entries
Source: https://cobo.com/developers/v2/api-references/addressbooks/create-address-book-entries

post /address_books
This operation adds new entries (records) to your Address Book.
<Note>This operation is available upon request. Please contact our [customer support](mailto:help@cobo.com) to enable it.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_address_books201_response import (
      CreateAddressBooks201Response,
  )
  from cobo_waas2.models.create_address_books_param import CreateAddressBooksParam
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AddressBooksApi(api_client)
      create_address_books_param = cobo_waas2.CreateAddressBooksParam(
          address_books=[
              cobo_waas2.CreateAddressBookParam(
                  chain_ids=["ETH"], address="0x570f02f2b5fcf3ac56fb6703bd7039c0c9e33460"
              )
          ]
      )

      try:
          # Create Address Book entries
          api_response = api_instance.create_address_books(
              create_address_books_param=create_address_books_param
          )
          print("The response of AddressBooksApi->create_address_books:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling AddressBooksApi->create_address_books: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AddressBooksApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AddressBooksApi apiInstance = new AddressBooksApi();
      CreateAddressBooksParam createAddressBooksParam =
          new CreateAddressBooksParam()
              .addressBooks(
                  Arrays.asList(
                      new CreateAddressBookParam()
                          .chainIds(Arrays.asList("ETH"))
                          .address("0x570f02f2b5fcf3ac56fb6703bd7039c0c9e33460")));
      try {
        CreateAddressBooks201Response result =
            apiInstance.createAddressBooks(createAddressBooksParam);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AddressBooksApi#createAddressBooks");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createAddressBooksParam := *coboWaas2.NewCreateAddressBooksParam([]coboWaas2.CreateAddressBookParam{*coboWaas2.NewCreateAddressBookParam([]string{"ETH"}, "0x570f02f2b5fcf3ac56fb6703bd7039c0c9e33460")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AddressBooksAPI.CreateAddressBooks(ctx).
  		CreateAddressBooksParam(createAddressBooksParam).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `AddressBooksAPI.CreateAddressBooks``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateAddressBooks`: CreateAddressBooks201Response
  	fmt.Fprintf(os.Stdout, "Response from `AddressBooksAPI.CreateAddressBooks`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AddressBooksApi();
  const opts = {
    CreateAddressBooksParam:
      CoboWaas2.CreateAddressBooksParam.constructFromObject({
        address_books: [
          {
            chain_ids: ["ETH"],
            address: "0x570f02f2b5fcf3ac56fb6703bd7039c0c9e33460",
          },
        ],
      }),
  };
  apiInstance.createAddressBooks(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Delete Address Book entry
Source: https://cobo.com/developers/v2/api-references/addressbooks/delete-address-book-entry

post /address_books/{entry_id}/delete
This operation deletes a specified Address Book entry (record).
<Note>This operation is available upon request. Please contact our [customer support](mailto:help@cobo.com) to enable it.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.delete_address_book_by_id201_response import (
      DeleteAddressBookById201Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AddressBooksApi(api_client)
      entry_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Delete Address Book entry
          api_response = api_instance.delete_address_book_by_id(entry_id)
          print("The response of AddressBooksApi->delete_address_book_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling AddressBooksApi->delete_address_book_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AddressBooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AddressBooksApi apiInstance = new AddressBooksApi();
      UUID entryId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        DeleteAddressBookById201Response result = apiInstance.deleteAddressBookById(entryId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AddressBooksApi#deleteAddressBookById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	entryId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AddressBooksAPI.DeleteAddressBookById(ctx, entryId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `AddressBooksAPI.DeleteAddressBookById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `DeleteAddressBookById`: DeleteAddressBookById201Response
  	fmt.Fprintf(os.Stdout, "Response from `AddressBooksAPI.DeleteAddressBookById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AddressBooksApi();
  const entry_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.deleteAddressBookById(entry_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get Address Book entry
Source: https://cobo.com/developers/v2/api-references/addressbooks/get-address-book-entry

get /address_books/{entry_id}
This operation retrieves the detailed information about a specified Address Book entry (record).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.address_book import AddressBook
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AddressBooksApi(api_client)
      entry_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get Address Book entry
          api_response = api_instance.get_address_book_by_id(entry_id)
          print("The response of AddressBooksApi->get_address_book_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling AddressBooksApi->get_address_book_by_id: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AddressBooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AddressBooksApi apiInstance = new AddressBooksApi();
      UUID entryId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        AddressBook result = apiInstance.getAddressBookById(entryId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AddressBooksApi#getAddressBookById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	entryId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AddressBooksAPI.GetAddressBookById(ctx, entryId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `AddressBooksAPI.GetAddressBookById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetAddressBookById`: AddressBook
  	fmt.Fprintf(os.Stdout, "Response from `AddressBooksAPI.GetAddressBookById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AddressBooksApi();
  const entry_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getAddressBookById(entry_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List Address Book entries
Source: https://cobo.com/developers/v2/api-references/addressbooks/list-address-book-entries

get /address_books
This operation retrieves all entries (records) from your Address Book. You can filter the entries by chain ID, address, and label.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_address_books200_response import ListAddressBooks200Response
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AddressBooksApi(api_client)
      chain_id = "ETH"
      address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
      label = "test"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List Address Book entries
          api_response = api_instance.list_address_books(
              chain_id=chain_id,
              address=address,
              label=label,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of AddressBooksApi->list_address_books:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling AddressBooksApi->list_address_books: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AddressBooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AddressBooksApi apiInstance = new AddressBooksApi();
      String chainId = "ETH";
      String address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045";
      String label = "test";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListAddressBooks200Response result =
            apiInstance.listAddressBooks(chainId, address, label, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AddressBooksApi#listAddressBooks");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	chainId := "ETH"
  	address := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
  	label := "test"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AddressBooksAPI.ListAddressBooks(ctx).
  		ChainId(chainId).
  		Address(address).
  		Label(label).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `AddressBooksAPI.ListAddressBooks``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListAddressBooks`: ListAddressBooks200Response
  	fmt.Fprintf(os.Stdout, "Response from `AddressBooksAPI.ListAddressBooks`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AddressBooksApi();
  const opts = {
    chain_id: "ETH",
    address: "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
    label: "test",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listAddressBooks(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Update Address Book entry
Source: https://cobo.com/developers/v2/api-references/addressbooks/update-address-book-entry

put /address_books/{entry_id}
This operation updates the information of a specified Address Book entry (record).
<Note>This operation is available upon request. Please contact our [customer support](mailto:help@cobo.com) to enable it.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.address_book import AddressBook
  from cobo_waas2.models.update_address_book_param import UpdateAddressBookParam
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AddressBooksApi(api_client)
      entry_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      update_address_book_param = cobo_waas2.UpdateAddressBookParam(chain_ids=["ETH"])

      try:
          # Update Address Book entry
          api_response = api_instance.update_address_book_by_id(
              entry_id, update_address_book_param=update_address_book_param
          )
          print("The response of AddressBooksApi->update_address_book_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling AddressBooksApi->update_address_book_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AddressBooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AddressBooksApi apiInstance = new AddressBooksApi();
      UUID entryId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      UpdateAddressBookParam updateAddressBookParam = new UpdateAddressBookParam().chainIds(Arrays.asList("ETH"));
      try {
        AddressBook result = apiInstance.updateAddressBookById(entryId, updateAddressBookParam);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AddressBooksApi#updateAddressBookById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	entryId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	updateAddressBookParam := *coboWaas2.NewUpdateAddressBookParam([]string{"ChainIds_example"})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AddressBooksAPI.UpdateAddressBookById(ctx, entryId).
  		UpdateAddressBookParam(updateAddressBookParam).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `AddressBooksAPI.UpdateAddressBookById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UpdateAddressBookById`: AddressBook
  	fmt.Fprintf(os.Stdout, "Response from `AddressBooksAPI.UpdateAddressBookById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AddressBooksApi();
  const entry_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    UpdateAddressBookParam: CoboWaas2.UpdateAddressBookParam.constructFromObject({
      chain_ids: ["ETH"],
    }),
  };
  apiInstance.updateAddressBookById(entry_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Cancel auto sweep task
Source: https://cobo.com/developers/v2/api-references/autosweep/cancel-auto-sweep-task

post /auto_sweep/tasks/{task_id}/cancel
This operation cancels an in-progress auto sweep task by its ID.

Only tasks with the `Submitted` status can be cancelled. Tasks that have already
been processed (status `TransactionCreated`) cannot be cancelled.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.auto_sweep_task import AutoSweepTask
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AutoSweepApi(api_client)
      task_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Cancel auto sweep task
          api_response = api_instance.cancel_auto_sweep_task_by_id(task_id)
          print("The response of AutoSweepApi->cancel_auto_sweep_task_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling AutoSweepApi->cancel_auto_sweep_task_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AutoSweepApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AutoSweepApi apiInstance = new AutoSweepApi();
      UUID taskId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        AutoSweepTask result = apiInstance.cancelAutoSweepTaskById(taskId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AutoSweepApi#cancelAutoSweepTaskById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	taskId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AutoSweepAPI.CancelAutoSweepTaskById(ctx, taskId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `AutoSweepAPI.CancelAutoSweepTaskById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CancelAutoSweepTaskById`: AutoSweepTask
  	fmt.Fprintf(os.Stdout, "Response from `AutoSweepAPI.CancelAutoSweepTaskById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AutoSweepApi();
  const task_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.cancelAutoSweepTaskById(task_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create auto-sweep task
Source: https://cobo.com/developers/v2/api-references/autosweep/create-auto-sweep-task

post /auto_sweep/tasks
This operation creates an auto-sweep task for the specified wallet and token. The task triggers transactions to sweep the full balance of the specified token to the configured sweep-to address.

<Note>A sweep requires native chain coin to pay for gas. The gas must be available either in the source (deposit) address, or supplied by a configured Fee Station or Auto-Fuel. Reaching the deposit threshold alone does not trigger a sweep. If no gas is available, the sweep is blocked (for example, with an insufficient-balance error) or the Fee Station quota check fails. When a sweep is blocked, the reason is reported in the `failed_reasons` array of the auto-sweep task.</Note>

<Info>This operation is asynchronous. When the task is created, it is returned with `status` set to `Submitted` and an empty `transaction_ids` array; this is expected and does not indicate a failure. The `transaction_ids` array is populated only after `status` becomes `TransactionCreated`. To retrieve the transaction IDs, poll [Get auto-sweep task details](https://www.cobo.com/developers/v2/api-references/autosweep/get-auto-sweep-task-details) using the returned `task_id` until the status changes.</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.auto_sweep_task import AutoSweepTask
  from cobo_waas2.models.create_auto_sweep_task import CreateAutoSweepTask
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AutoSweepApi(api_client)
      create_auto_sweep_task = cobo_waas2.CreateAutoSweepTask(
          wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479", token_id="ETH_USDT"
      )

      try:
          # Create auto-sweep task
          api_response = api_instance.create_auto_sweep_task(
              create_auto_sweep_task=create_auto_sweep_task
          )
          print("The response of AutoSweepApi->create_auto_sweep_task:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling AutoSweepApi->create_auto_sweep_task: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AutoSweepApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AutoSweepApi apiInstance = new AutoSweepApi();
      CreateAutoSweepTask createAutoSweepTask =
          new CreateAutoSweepTask()
              .walletId("f47ac10b-58cc-4372-a567-0e02b2c3d479")
              .tokenId("ETH_USDT");
      try {
        AutoSweepTask result = apiInstance.createAutoSweepTask(createAutoSweepTask);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AutoSweepApi#createAutoSweepTask");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createAutoSweepTask := *coboWaas2.NewCreateAutoSweepTask("f47ac10b-58cc-4372-a567-0e02b2c3d479", "ETH_USDT")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AutoSweepAPI.CreateAutoSweepTask(ctx).
  		CreateAutoSweepTask(createAutoSweepTask).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `AutoSweepAPI.CreateAutoSweepTask``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateAutoSweepTask`: AutoSweepTask
  	fmt.Fprintf(os.Stdout, "Response from `AutoSweepAPI.CreateAutoSweepTask`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AutoSweepApi();
  const opts = {
    CreateAutoSweepTask: CoboWaas2.CreateAutoSweepTask.constructFromObject({
      wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
      token_id: "ETH_USDT",
    }),
  };
  apiInstance.createAutoSweepTask(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create sweep-to address
Source: https://cobo.com/developers/v2/api-references/autosweep/create-sweep-to-address

post /auto_sweep/sweep_to_addresses
This operation creates a new sweep-to address for the specified wallet. The previously sweep-to address for the same token becomes invalid once the new one is created.

Use this operation to change the sweep-to address when your setup changes, you switch networks, or the current address is compromised or tainted by suspicious funds. You can withdraw any remaining balances from the old sweep-to addresses to the new address or another designated destination.

<Note>Sweep-to addresses are only applicable to MPC Wallets and Custodial Wallets (Web3 Wallets) with the auto-sweep feature enabled.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_sweep_to_address import CreateSweepToAddress
  from cobo_waas2.models.sweep_to_address import SweepToAddress
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AutoSweepApi(api_client)
      create_sweep_to_address = cobo_waas2.CreateSweepToAddress(
          wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479", chain_id="ETH"
      )

      try:
          # Create sweep-to address
          api_response = api_instance.create_wallet_sweep_to_addresses(
              create_sweep_to_address=create_sweep_to_address
          )
          print("The response of AutoSweepApi->create_wallet_sweep_to_addresses:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling AutoSweepApi->create_wallet_sweep_to_addresses: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AutoSweepApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AutoSweepApi apiInstance = new AutoSweepApi();
      CreateSweepToAddress createSweepToAddress =
          new CreateSweepToAddress().walletId("f47ac10b-58cc-4372-a567-0e02b2c3d479").chainId("ETH");
      try {
        SweepToAddress result = apiInstance.createWalletSweepToAddresses(createSweepToAddress);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AutoSweepApi#createWalletSweepToAddresses");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createSweepToAddress := *coboWaas2.NewCreateSweepToAddress("f47ac10b-58cc-4372-a567-0e02b2c3d479", "ETH")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AutoSweepAPI.CreateWalletSweepToAddresses(ctx).
  		CreateSweepToAddress(createSweepToAddress).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `AutoSweepAPI.CreateWalletSweepToAddresses``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateWalletSweepToAddresses`: SweepToAddress
  	fmt.Fprintf(os.Stdout, "Response from `AutoSweepAPI.CreateWalletSweepToAddresses`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AutoSweepApi();
  const opts = {
    CreateSweepToAddress: CoboWaas2.CreateSweepToAddress.constructFromObject({
      wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
      chain_id: "ETH",
    }),
  };
  apiInstance.createWalletSweepToAddresses(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get auto-sweep task details
Source: https://cobo.com/developers/v2/api-references/autosweep/get-auto-sweep-task-details

get /auto_sweep/tasks/{task_id}
This operation retrieves detailed information about a specified auto-sweep task.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.auto_sweep_task import AutoSweepTask
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AutoSweepApi(api_client)
      task_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get auto-sweep task details
          api_response = api_instance.get_auto_sweep_task_by_id(task_id)
          print("The response of AutoSweepApi->get_auto_sweep_task_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling AutoSweepApi->get_auto_sweep_task_by_id: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AutoSweepApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AutoSweepApi apiInstance = new AutoSweepApi();
      UUID taskId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        AutoSweepTask result = apiInstance.getAutoSweepTaskById(taskId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AutoSweepApi#getAutoSweepTaskById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	taskId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AutoSweepAPI.GetAutoSweepTaskById(ctx, taskId).Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `AutoSweepAPI.GetAutoSweepTaskById``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetAutoSweepTaskById`: AutoSweepTask
  	fmt.Fprintf(os.Stdout, "Response from `AutoSweepAPI.GetAutoSweepTaskById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AutoSweepApi();
  const task_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getAutoSweepTaskById(task_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List auto-sweep tasks
Source: https://cobo.com/developers/v2/api-references/autosweep/list-auto-sweep-tasks

get /auto_sweep/tasks
This operation retrieves a list of auto-sweep tasks for the specified wallet. You can filter the results by token ID, task IDs, or a created-time range.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_auto_sweep_task200_response import (
      ListAutoSweepTask200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AutoSweepApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      token_id = "ETH_USDT"
      task_ids = (
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,1ddca562-8434-41c9-8809-d437bad9c868"
      )
      min_created_timestamp = 1635744000000
      max_created_timestamp = 1635744000000
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
      direction = "ASC"

      try:
          # List auto-sweep tasks
          api_response = api_instance.list_auto_sweep_task(
              wallet_id,
              token_id=token_id,
              task_ids=task_ids,
              min_created_timestamp=min_created_timestamp,
              max_created_timestamp=max_created_timestamp,
              limit=limit,
              before=before,
              after=after,
              direction=direction,
          )
          print("The response of AutoSweepApi->list_auto_sweep_task:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling AutoSweepApi->list_auto_sweep_task: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AutoSweepApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AutoSweepApi apiInstance = new AutoSweepApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String tokenId = "ETH_USDT";
      String taskIds = "f47ac10b-58cc-4372-a567-0e02b2c3d479,1ddca562-8434-41c9-8809-d437bad9c868";
      Long minCreatedTimestamp = 1635744000000L;
      Long maxCreatedTimestamp = 1635744000000L;
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      String direction = "ASC";
      try {
        ListAutoSweepTask200Response result =
            apiInstance.listAutoSweepTask(
                walletId,
                tokenId,
                taskIds,
                minCreatedTimestamp,
                maxCreatedTimestamp,
                limit,
                before,
                after,
                direction);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AutoSweepApi#listAutoSweepTask");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	tokenId := "ETH_USDT"
  	taskIds := "f47ac10b-58cc-4372-a567-0e02b2c3d479,1ddca562-8434-41c9-8809-d437bad9c868"
  	minCreatedTimestamp := int64(1635744000000)
  	maxCreatedTimestamp := int64(1635744000000)
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
  	direction := "ASC"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AutoSweepAPI.ListAutoSweepTask(ctx).
  		WalletId(walletId).
  		TokenId(tokenId).
  		TaskIds(taskIds).
  		MinCreatedTimestamp(minCreatedTimestamp).
  		MaxCreatedTimestamp(maxCreatedTimestamp).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Direction(direction).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `AutoSweepAPI.ListAutoSweepTask``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListAutoSweepTask`: ListAutoSweepTask200Response
  	fmt.Fprintf(os.Stdout, "Response from `AutoSweepAPI.ListAutoSweepTask`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AutoSweepApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    token_id: "ETH_USDT",
    task_ids:
      "f47ac10b-58cc-4372-a567-0e02b2c3d479,1ddca562-8434-41c9-8809-d437bad9c868",
    min_created_timestamp: 1635744000000,
    max_created_timestamp: 1635744000000,
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
    direction: "ASC",
  };
  apiInstance.listAutoSweepTask(wallet_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List sweep-to addresses
Source: https://cobo.com/developers/v2/api-references/autosweep/list-sweep-to-addresses

get /auto_sweep/sweep_to_addresses
This operation retrieves a list of sweep-to addresses within your wallet.

<Note>Sweep-to addresses are only applicable to MPC Wallets and Custodial Wallets (Web3 Wallets) with the auto-sweep feature enabled.</Note>

<Info>For EVM-compatible chains (such as Ethereum and BNB Smart Chain), the same address is used across chains. As a result, when listing sweep-to addresses, only one address entry (shown under Ethereum) is returned for all EVM-compatible chains. Separate entries are not returned for each individual EVM chain.</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_wallet_sweep_to_addresses200_response import (
      ListWalletSweepToAddresses200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AutoSweepApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # List sweep-to addresses
          api_response = api_instance.list_wallet_sweep_to_addresses(wallet_id)
          print("The response of AutoSweepApi->list_wallet_sweep_to_addresses:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling AutoSweepApi->list_wallet_sweep_to_addresses: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AutoSweepApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AutoSweepApi apiInstance = new AutoSweepApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        ListWalletSweepToAddresses200Response result =
            apiInstance.listWalletSweepToAddresses(walletId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AutoSweepApi#listWalletSweepToAddresses");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AutoSweepAPI.ListWalletSweepToAddresses(ctx).
  		WalletId(walletId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `AutoSweepAPI.ListWalletSweepToAddresses``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListWalletSweepToAddresses`: ListWalletSweepToAddresses200Response
  	fmt.Fprintf(os.Stdout, "Response from `AutoSweepAPI.ListWalletSweepToAddresses`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AutoSweepApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.listWalletSweepToAddresses(wallet_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get disposition status
Source: https://cobo.com/developers/v2/api-references/compliance/get-disposition-status

get /compliance/funds/disposition
This operation retrieves the current status of a disposition request for a specific transaction.

You can use this endpoint to check the status of any disposition operation (Refund, Isolate, or Unfreeze) 
that has been initiated for a transaction. The response includes the disposition type, current status, 
and the disposition transaction ID if applicable.

<Note>Use this endpoint to monitor the progress of disposition operations and verify their completion.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.disposition_query_response import DispositionQueryResponse
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.ComplianceApi(api_client)
      transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get disposition status
          api_response = api_instance.get_disposition_status(transaction_id)
          print("The response of ComplianceApi->get_disposition_status:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling ComplianceApi->get_disposition_status: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.ComplianceApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      ComplianceApi apiInstance = new ComplianceApi();
      UUID transactionId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        DispositionQueryResponse result = apiInstance.getDispositionStatus(transactionId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling ComplianceApi#getDispositionStatus");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.ComplianceAPI.GetDispositionStatus(ctx).
  		TransactionId(transactionId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `ComplianceAPI.GetDispositionStatus``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetDispositionStatus`: DispositionQueryResponse
  	fmt.Fprintf(os.Stdout, "Response from `ComplianceAPI.GetDispositionStatus`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.ComplianceApi();
  const transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getDispositionStatus(transaction_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get KYT screening status
Source: https://cobo.com/developers/v2/api-references/compliance/get-kyt-screening-status

get /compliance/kyt/screenings/status
This operation retrieves the current KYT (Know Your Transaction) screening status, including review status and fund disposition status, for a specific transaction.

Use this endpoint to monitor the real-time screening progress for transactions processed through the KYT compliance system.

<Note>This endpoint provides comprehensive compliance monitoring capabilities to help maintain AML (Anti-Money Laundering) regulatory compliance and audit trail requirements.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.kyt_screenings_transaction import KytScreeningsTransaction
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.ComplianceApi(api_client)
      transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get KYT screening status
          api_response = api_instance.get_kyt_screening_status(transaction_id)
          print("The response of ComplianceApi->get_kyt_screening_status:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling ComplianceApi->get_kyt_screening_status: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.ComplianceApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      ComplianceApi apiInstance = new ComplianceApi();
      UUID transactionId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        KytScreeningsTransaction result = apiInstance.getKytScreeningStatus(transactionId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling ComplianceApi#getKytScreeningStatus");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.ComplianceAPI.GetKytScreeningStatus(ctx).
  		TransactionId(transactionId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `ComplianceAPI.GetKytScreeningStatus``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetKytScreeningStatus`: KytScreeningsTransaction
  	fmt.Fprintf(os.Stdout, "Response from `ComplianceAPI.GetKytScreeningStatus`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.ComplianceApi();
  const transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getKytScreeningStatus(transaction_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Isolate funds
Source: https://cobo.com/developers/v2/api-references/compliance/isolate-funds

post /compliance/funds/disposition/isolate
This operation creates a request to isolate funds for a specific transaction. The funds will be sent to a designated isolation address for compliance purposes.

You need to specify the transaction ID to be isolated and the destination address. 
Optional parameters include custom categories for tracking purposes.

<Note>The isolation will initiate a withdrawal transaction from the compliance-managed address to the specified isolation address.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.disposition_response import DispositionResponse
  from cobo_waas2.models.isolate_disposition import IsolateDisposition
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.ComplianceApi(api_client)
      isolate_disposition = cobo_waas2.IsolateDisposition()

      try:
          # Isolate funds
          api_response = api_instance.isolate_funds(
              isolate_disposition=isolate_disposition
          )
          print("The response of ComplianceApi->isolate_funds:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling ComplianceApi->isolate_funds: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.ComplianceApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      ComplianceApi apiInstance = new ComplianceApi();
      IsolateDisposition isolateDisposition = new IsolateDisposition();
      try {
        DispositionResponse result = apiInstance.isolateFunds(isolateDisposition);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling ComplianceApi#isolateFunds");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	isolateDisposition := *coboWaas2.NewIsolateDisposition("f47ac10b-58cc-4372-a567-0e02b2c3d479", "0x742d35Cc6634C0532925a3b844Bc9e7595f0bEb7", "1.5")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.ComplianceAPI.IsolateFunds(ctx).
  		IsolateDisposition(isolateDisposition).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `ComplianceAPI.IsolateFunds``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `IsolateFunds`: DispositionResponse
  	fmt.Fprintf(os.Stdout, "Response from `ComplianceAPI.IsolateFunds`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.ComplianceApi();
  const opts = {
    IsolateDisposition: new CoboWaas2.IsolateDisposition(),
  };
  apiInstance.isolateFunds(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Refund funds
Source: https://cobo.com/developers/v2/api-references/compliance/refund-funds

post /compliance/funds/disposition/refund
This operation creates a request to refund funds for a specific transaction. The funds will be sent to the specified destination address.

You need to specify the transaction ID to be refunded and the destination address. 
Optional parameters include custom categories for tracking purposes.

<Note>The refund will initiate a withdrawal transaction from the compliance-managed address to the specified destination.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.disposition_response import DispositionResponse
  from cobo_waas2.models.refund_disposition import RefundDisposition
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.ComplianceApi(api_client)
      refund_disposition = cobo_waas2.RefundDisposition()

      try:
          # Refund funds
          api_response = api_instance.refund_funds(refund_disposition=refund_disposition)
          print("The response of ComplianceApi->refund_funds:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling ComplianceApi->refund_funds: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.ComplianceApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      ComplianceApi apiInstance = new ComplianceApi();
      RefundDisposition refundDisposition = new RefundDisposition();
      try {
        DispositionResponse result = apiInstance.refundFunds(refundDisposition);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling ComplianceApi#refundFunds");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	refundDisposition := *coboWaas2.NewRefundDisposition("f47ac10b-58cc-4372-a567-0e02b2c3d479", "0x742d35Cc6634C0532925a3b844Bc9e7595f0bEb7", "1.5")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.ComplianceAPI.RefundFunds(ctx).
  		RefundDisposition(refundDisposition).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `ComplianceAPI.RefundFunds``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `RefundFunds`: DispositionResponse
  	fmt.Fprintf(os.Stdout, "Response from `ComplianceAPI.RefundFunds`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.ComplianceApi();
  const opts = {
    RefundDisposition: new CoboWaas2.RefundDisposition(),
  };
  apiInstance.refundFunds(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Submit KYT manual review result
Source: https://cobo.com/developers/v2/api-references/compliance/submit-kyt-manual-review-result

post /compliance/kyt/screenings/manual_review
This operation submits a manual review result for a KYT (Know Your Transaction) screening case that requires human analysis.

Use this endpoint when transactions flagged for manual review have been analyzed by compliance officers and require submission of review outcomes with detailed comments and justifications.

This endpoint is specifically designed for submitting comprehensive manual review findings rather than automated screening decisions.

<Note>Submitting a manual review result will update the KYT screening status and initiate appropriate compliance workflow actions based on the review outcome.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.submit_kyt_response import SubmitKytResponse
  from cobo_waas2.models.submit_kyt_screenings_review_body import (
      SubmitKytScreeningsReviewBody,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.ComplianceApi(api_client)
      submit_kyt_screenings_review_body = cobo_waas2.SubmitKytScreeningsReviewBody(
          transaction_id="f47ac10b-58cc-4372-a567-0e02b2c3d479", result="Approval"
      )

      try:
          # Submit KYT manual review result
          api_response = api_instance.submit_kyt_manual_review(
              submit_kyt_screenings_review_body=submit_kyt_screenings_review_body
          )
          print("The response of ComplianceApi->submit_kyt_manual_review:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling ComplianceApi->submit_kyt_manual_review: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.ComplianceApi;
  import com.cobo.waas2.model.*;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      ComplianceApi apiInstance = new ComplianceApi();
      SubmitKytScreeningsReviewBody submitKytScreeningsReviewBody =
          new SubmitKytScreeningsReviewBody()
              .transactionId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
              .result(KytScreeningsReviewType.APPROVAL);
      try {
        SubmitKytResponse result = apiInstance.submitKytManualReview(submitKytScreeningsReviewBody);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling ComplianceApi#submitKytManualReview");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	submitKytScreeningsReviewBody := *coboWaas2.NewSubmitKytScreeningsReviewBody("f47ac10b-58cc-4372-a567-0e02b2c3d479", coboWaas2.KytScreeningsReviewType("Approval"))

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.ComplianceAPI.SubmitKytManualReview(ctx).
  		SubmitKytScreeningsReviewBody(submitKytScreeningsReviewBody).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `ComplianceAPI.SubmitKytManualReview``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `SubmitKytManualReview`: SubmitKytResponse
  	fmt.Fprintf(os.Stdout, "Response from `ComplianceAPI.SubmitKytManualReview`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.ComplianceApi();
  const opts = {
    SubmitKytScreeningsReviewBody:
      CoboWaas2.SubmitKytScreeningsReviewBody.constructFromObject({
        transaction_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
        result: "Approval",
      }),
  };
  apiInstance.submitKytManualReview(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Submit KYT screening decision
Source: https://cobo.com/developers/v2/api-references/compliance/submit-kyt-screening-decision

post /compliance/kyt/screenings/decisions
This operation submits a KYT (Know Your Transaction) screening decision for a specific transaction based on an external compliance review.

Use this endpoint to provide a screening decision (Approval, ApprovalWithAlert, Rejection, or ManualReview) after completing the external KYT screening process.

The submitted decision will be recorded for compliance audit purposes and regulatory reporting requirements.

<Note>Submitting a screening decision will update the transaction's KYT status and may automatically trigger downstream compliance workflows or notifications depending on the decision type.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.submit_kyt_response import SubmitKytResponse
  from cobo_waas2.models.submit_kyt_screenings_decisions_body import (
      SubmitKytScreeningsDecisionsBody,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.ComplianceApi(api_client)
      submit_kyt_screenings_decisions_body = cobo_waas2.SubmitKytScreeningsDecisionsBody(
          transaction_id="f47ac10b-58cc-4372-a567-0e02b2c3d479", result="Approval"
      )

      try:
          # Submit KYT screening decision
          api_response = api_instance.submit_kyt_screening_decisions(
              submit_kyt_screenings_decisions_body=submit_kyt_screenings_decisions_body
          )
          print("The response of ComplianceApi->submit_kyt_screening_decisions:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling ComplianceApi->submit_kyt_screening_decisions: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.ComplianceApi;
  import com.cobo.waas2.model.*;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      ComplianceApi apiInstance = new ComplianceApi();
      SubmitKytScreeningsDecisionsBody submitKytScreeningsDecisionsBody =
          new SubmitKytScreeningsDecisionsBody()
              .transactionId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
              .result(KytScreeningsDecisionsType.APPROVAL);
      try {
        SubmitKytResponse result =
            apiInstance.submitKytScreeningDecisions(submitKytScreeningsDecisionsBody);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling ComplianceApi#submitKytScreeningDecisions");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	submitKytScreeningsDecisionsBody := *coboWaas2.NewSubmitKytScreeningsDecisionsBody("f47ac10b-58cc-4372-a567-0e02b2c3d479", coboWaas2.KytScreeningsDecisionsType("Approval"))

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.ComplianceAPI.SubmitKytScreeningDecisions(ctx).
  		SubmitKytScreeningsDecisionsBody(submitKytScreeningsDecisionsBody).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `ComplianceAPI.SubmitKytScreeningDecisions``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `SubmitKytScreeningDecisions`: SubmitKytResponse
  	fmt.Fprintf(os.Stdout, "Response from `ComplianceAPI.SubmitKytScreeningDecisions`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.ComplianceApi();
  const opts = {
    SubmitKytScreeningsDecisionsBody:
      CoboWaas2.SubmitKytScreeningsDecisionsBody.constructFromObject({
        transaction_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
        result: "Approval",
      }),
  };
  apiInstance.submitKytScreeningDecisions(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Unfreeze frozen funds
Source: https://cobo.com/developers/v2/api-references/compliance/unfreeze-frozen-funds

post /compliance/funds/disposition/unfreeze
This operation creates a request to unfreeze funds for a previously frozen transaction. It releases the frozen funds back to their original state.

You only need to specify the transaction ID to be unfrozen. Once unfrozen, the funds will be available for normal operations.

<Note>The unfreeze process will release the compliance hold on the transaction, allowing it to proceed normally.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.disposition_response import DispositionResponse
  from cobo_waas2.models.unfreeze_disposition import UnfreezeDisposition
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.ComplianceApi(api_client)
      unfreeze_disposition = cobo_waas2.UnfreezeDisposition()

      try:
          # Unfreeze frozen funds
          api_response = api_instance.unfreeze_funds(
              unfreeze_disposition=unfreeze_disposition
          )
          print("The response of ComplianceApi->unfreeze_funds:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling ComplianceApi->unfreeze_funds: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.ComplianceApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      ComplianceApi apiInstance = new ComplianceApi();
      UnfreezeDisposition unfreezeDisposition = new UnfreezeDisposition();
      try {
        DispositionResponse result = apiInstance.unfreezeFunds(unfreezeDisposition);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling ComplianceApi#unfreezeFunds");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	unfreezeDisposition := *coboWaas2.NewUnfreezeDisposition("f47ac10b-58cc-4372-a567-0e02b2c3d479")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.ComplianceAPI.UnfreezeFunds(ctx).
  		UnfreezeDisposition(unfreezeDisposition).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `ComplianceAPI.UnfreezeFunds``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UnfreezeFunds`: DispositionResponse
  	fmt.Fprintf(os.Stdout, "Response from `ComplianceAPI.UnfreezeFunds`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.ComplianceApi();
  const opts = {
    UnfreezeDisposition: new CoboWaas2.UnfreezeDisposition(),
  };
  apiInstance.unfreezeFunds(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get webhook endpoint information
Source: https://cobo.com/developers/v2/api-references/developers--webhooks/get-webhook-endpoint-information

get /webhooks/endpoints/{endpoint_id}
This operation retrieves the information of a specified webhook endpoint.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.webhook_endpoint import WebhookEndpoint
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersWebhooksApi(api_client)
      endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get webhook endpoint information
          api_response = api_instance.get_webhook_endpoint_by_id(endpoint_id)
          print("The response of DevelopersWebhooksApi->get_webhook_endpoint_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling DevelopersWebhooksApi->get_webhook_endpoint_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersWebhooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersWebhooksApi apiInstance = new DevelopersWebhooksApi();
      UUID endpointId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        WebhookEndpoint result = apiInstance.getWebhookEndpointById(endpointId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersWebhooksApi#getWebhookEndpointById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	endpointId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersWebhooksAPI.GetWebhookEndpointById(ctx, endpointId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersWebhooksAPI.GetWebhookEndpointById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetWebhookEndpointById`: WebhookEndpoint
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `DevelopersWebhooksAPI.GetWebhookEndpointById`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersWebhooksApi();
  const endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getWebhookEndpointById(endpoint_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get webhook event types
Source: https://cobo.com/developers/v2/api-references/developers--webhooks/get-webhook-event-types

get /webhooks/events/definitions
This operation retrieves all supported webhook event types.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_webhook_event_definitions200_response_inner import (
      ListWebhookEventDefinitions200ResponseInner,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersWebhooksApi(api_client)

      try:
          # Get webhook event types
          api_response = api_instance.list_webhook_event_definitions()
          print(
              "The response of DevelopersWebhooksApi->list_webhook_event_definitions:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling DevelopersWebhooksApi->list_webhook_event_definitions: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersWebhooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersWebhooksApi apiInstance = new DevelopersWebhooksApi();
      try {
        List<ListWebhookEventDefinitions200ResponseInner> result =
            apiInstance.listWebhookEventDefinitions();
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling DevelopersWebhooksApi#listWebhookEventDefinitions");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersWebhooksAPI.ListWebhookEventDefinitions(ctx).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersWebhooksAPI.ListWebhookEventDefinitions``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListWebhookEventDefinitions`: []ListWebhookEventDefinitions200ResponseInner
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `DevelopersWebhooksAPI.ListWebhookEventDefinitions`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersWebhooksApi();
  apiInstance.listWebhookEventDefinitions().then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List all webhook events
Source: https://cobo.com/developers/v2/api-references/developers--webhooks/list-all-webhook-events

get /webhooks/endpoints/{endpoint_id}/events
This operation retrieves a list of webhook events that have occurred within the last 30 days.

<Note>The request will only return webhook events that have occurred to the wallets associated with your current API key. For example, if the current API key is only associated with Custodial Wallets, any webhook events that have occurred to an MPC Wallet will not be retrieved with the current API key.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_webhook_events200_response import (
      ListWebhookEvents200Response,
  )
  from cobo_waas2.models.webhook_event_status import WebhookEventStatus
  from cobo_waas2.models.webhook_event_type import WebhookEventType
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersWebhooksApi(api_client)
      endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      status = cobo_waas2.WebhookEventStatus()
      type = cobo_waas2.WebhookEventType()
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List all webhook events
          api_response = api_instance.list_webhook_events(
              endpoint_id,
              status=status,
              type=type,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of DevelopersWebhooksApi->list_webhook_events:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling DevelopersWebhooksApi->list_webhook_events: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersWebhooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersWebhooksApi apiInstance = new DevelopersWebhooksApi();
      UUID endpointId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      WebhookEventStatus status = WebhookEventStatus.fromValue("Success");
      WebhookEventType type = WebhookEventType.fromValue("wallets.transaction.created");
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListWebhookEvents200Response result =
            apiInstance.listWebhookEvents(endpointId, status, type, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersWebhooksApi#listWebhookEvents");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	endpointId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	status := coboWaas2.WebhookEventStatus("Success")
  	type_ := coboWaas2.WebhookEventType("wallets.transaction.created")
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersWebhooksAPI.ListWebhookEvents(ctx, endpointId).
  		Status(status).
  		Type_(type_).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersWebhooksAPI.ListWebhookEvents``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListWebhookEvents`: ListWebhookEvents200Response
  	fmt.Fprintf(os.Stdout, "Response from `DevelopersWebhooksAPI.ListWebhookEvents`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersWebhooksApi();
  const endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    status: new CoboWaas2.WebhookEventStatus(),
    type: new CoboWaas2.WebhookEventType(),
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listWebhookEvents(endpoint_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List webhook endpoints
Source: https://cobo.com/developers/v2/api-references/developers--webhooks/list-webhook-endpoints

get /webhooks/endpoints
This operation retrieves the information of all webhook endpoints registered under your organization. You can filter the result by endpoint status and the subscribed event type.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_webhook_endpoints200_response import (
      ListWebhookEndpoints200Response,
  )
  from cobo_waas2.models.webhook_endpoint_status import WebhookEndpointStatus
  from cobo_waas2.models.webhook_event_type import WebhookEventType
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersWebhooksApi(api_client)
      status = cobo_waas2.WebhookEndpointStatus()
      event_type = cobo_waas2.WebhookEventType()
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List webhook endpoints
          api_response = api_instance.list_webhook_endpoints(
              status=status,
              event_type=event_type,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of DevelopersWebhooksApi->list_webhook_endpoints:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling DevelopersWebhooksApi->list_webhook_endpoints: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersWebhooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersWebhooksApi apiInstance = new DevelopersWebhooksApi();
      WebhookEndpointStatus status = WebhookEndpointStatus.fromValue("STATUS_ACTIVE");
      WebhookEventType eventType = WebhookEventType.fromValue("wallets.transaction.created");
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListWebhookEndpoints200Response result =
            apiInstance.listWebhookEndpoints(status, eventType, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersWebhooksApi#listWebhookEndpoints");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	status := coboWaas2.WebhookEndpointStatus("STATUS_ACTIVE")
  	eventType := coboWaas2.WebhookEventType("wallets.transaction.created")
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersWebhooksAPI.ListWebhookEndpoints(ctx).
  		Status(status).
  		EventType(eventType).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersWebhooksAPI.ListWebhookEndpoints``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListWebhookEndpoints`: ListWebhookEndpoints200Response
  	fmt.Fprintf(os.Stdout, "Response from `DevelopersWebhooksAPI.ListWebhookEndpoints`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersWebhooksApi();
  const opts = {
    status: new CoboWaas2.WebhookEndpointStatus(),
    event_type: new CoboWaas2.WebhookEventType(),
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listWebhookEndpoints(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List webhook event logs
Source: https://cobo.com/developers/v2/api-references/developers--webhooks/list-webhook-event-logs

get /webhooks/endpoints/{endpoint_id}/events/{event_id}/logs
This operation retrieves a list of webhook event logs by event ID. Each retry will generate a separate event log.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_webhook_event_logs200_response import (
      ListWebhookEventLogs200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersWebhooksApi(api_client)
      event_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List webhook event logs
          api_response = api_instance.list_webhook_event_logs(
              event_id, endpoint_id, limit=limit, before=before, after=after
          )
          print("The response of DevelopersWebhooksApi->list_webhook_event_logs:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling DevelopersWebhooksApi->list_webhook_event_logs: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersWebhooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersWebhooksApi apiInstance = new DevelopersWebhooksApi();
      UUID eventId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      UUID endpointId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListWebhookEventLogs200Response result =
            apiInstance.listWebhookEventLogs(eventId, endpointId, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersWebhooksApi#listWebhookEventLogs");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	eventId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	endpointId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersWebhooksAPI.ListWebhookEventLogs(ctx, eventId, endpointId).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersWebhooksAPI.ListWebhookEventLogs``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListWebhookEventLogs`: ListWebhookEventLogs200Response
  	fmt.Fprintf(os.Stdout, "Response from `DevelopersWebhooksAPI.ListWebhookEventLogs`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersWebhooksApi();
  const event_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listWebhookEventLogs(event_id, endpoint_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Register webhook endpoint
Source: https://cobo.com/developers/v2/api-references/developers--webhooks/register-webhook-endpoint

post /webhooks/endpoints
This operation registers a new webhook endpoint for your organization.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_webhook_endpoint_request import (
      CreateWebhookEndpointRequest,
  )
  from cobo_waas2.models.webhook_endpoint import WebhookEndpoint
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersWebhooksApi(api_client)
      create_webhook_endpoint_request = cobo_waas2.CreateWebhookEndpointRequest(
          url="https://example.com/webhook",
          subscribed_events=["wallets.transaction.created"],
      )

      try:
          # Register webhook endpoint
          api_response = api_instance.create_webhook_endpoint(
              create_webhook_endpoint_request=create_webhook_endpoint_request
          )
          print("The response of DevelopersWebhooksApi->create_webhook_endpoint:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling DevelopersWebhooksApi->create_webhook_endpoint: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersWebhooksApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersWebhooksApi apiInstance = new DevelopersWebhooksApi();
      CreateWebhookEndpointRequest createWebhookEndpointRequest =
          new CreateWebhookEndpointRequest()
              .url("https://example.com/webhook")
              .subscribedEvents(Arrays.asList(WebhookEventType.WALLETS_TRANSACTION_CREATED));
      try {
        WebhookEndpoint result = apiInstance.createWebhookEndpoint(createWebhookEndpointRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersWebhooksApi#createWebhookEndpoint");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createWebhookEndpointRequest := *coboWaas2.NewCreateWebhookEndpointRequest("https://example.com/webhook", []coboWaas2.WebhookEventType{coboWaas2.WebhookEventType("wallets.transaction.created")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersWebhooksAPI.CreateWebhookEndpoint(ctx).
  		CreateWebhookEndpointRequest(createWebhookEndpointRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersWebhooksAPI.CreateWebhookEndpoint``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateWebhookEndpoint`: WebhookEndpoint
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `DevelopersWebhooksAPI.CreateWebhookEndpoint`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersWebhooksApi();
  const opts = {
    CreateWebhookEndpointRequest:
      CoboWaas2.CreateWebhookEndpointRequest.constructFromObject({
        url: "https://example.com/webhook",
        subscribed_events: ["wallets.transaction.created"],
      }),
  };
  apiInstance.createWebhookEndpoint(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Retrieve event information
Source: https://cobo.com/developers/v2/api-references/developers--webhooks/retrieve-event-information

get /webhooks/endpoints/{endpoint_id}/events/{event_id}
This operation retrieves the information of a webhook event by the event ID.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.webhook_event import WebhookEvent
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersWebhooksApi(api_client)
      event_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Retrieve event information
          api_response = api_instance.get_webhook_event_by_id(event_id, endpoint_id)
          print("The response of DevelopersWebhooksApi->get_webhook_event_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling DevelopersWebhooksApi->get_webhook_event_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersWebhooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersWebhooksApi apiInstance = new DevelopersWebhooksApi();
      UUID eventId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      UUID endpointId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        WebhookEvent result = apiInstance.getWebhookEventById(eventId, endpointId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersWebhooksApi#getWebhookEventById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	eventId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	endpointId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersWebhooksAPI.GetWebhookEventById(ctx, eventId, endpointId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersWebhooksAPI.GetWebhookEventById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetWebhookEventById`: WebhookEvent
  	fmt.Fprintf(os.Stdout, "Response from `DevelopersWebhooksAPI.GetWebhookEventById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersWebhooksApi();
  const event_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getWebhookEventById(event_id, endpoint_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Retry event
Source: https://cobo.com/developers/v2/api-references/developers--webhooks/retry-event

post /webhooks/endpoints/{endpoint_id}/events/{event_id}/retry
This operation retries delivering a webhook event with the specified event ID. You can only retry delivering a webhook event in the `Retrying` or `Failed` status.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.retry_webhook_event_by_id201_response import (
      RetryWebhookEventById201Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersWebhooksApi(api_client)
      event_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Retry event
          api_response = api_instance.retry_webhook_event_by_id(event_id, endpoint_id)
          print("The response of DevelopersWebhooksApi->retry_webhook_event_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling DevelopersWebhooksApi->retry_webhook_event_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersWebhooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersWebhooksApi apiInstance = new DevelopersWebhooksApi();
      UUID eventId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      UUID endpointId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        RetryWebhookEventById201Response result =
            apiInstance.retryWebhookEventById(eventId, endpointId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersWebhooksApi#retryWebhookEventById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	eventId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	endpointId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersWebhooksAPI.RetryWebhookEventById(ctx, eventId, endpointId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersWebhooksAPI.RetryWebhookEventById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `RetryWebhookEventById`: RetryWebhookEventById201Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `DevelopersWebhooksAPI.RetryWebhookEventById`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersWebhooksApi();
  const event_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.retryWebhookEventById(event_id, endpoint_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Trigger test event
Source: https://cobo.com/developers/v2/api-references/developers--webhooks/trigger-test-event

post /webhooks/events/trigger
This operation tests the functionality of your webhook endpoint by triggering a test webhook event. The test event will be sent to all the endpoints you have registered on Cobo Portal.

You only need to provide the event type. By default, the payload contains dummy data with no impact on your real business transactions or activities. You can optionally provide the `override_data` property to customize the payload.

<Note>Currently, you can only trigger test webhook events with the event data types [`Transaction`](https://www.cobo.com/developers/v2/guides/webhooks-callbacks/webhook-event-type#transaction-events-deposits%2Fwithdrawals%2Fcontract-calls%2Fmessage-signing) and [`TSSRequest`](https://www.cobo.com/developers/v2/guides/webhooks-callbacks/webhook-event-type#mpc-tss-request-events).</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.trigger_test_webhook_event201_response import (
      TriggerTestWebhookEvent201Response,
  )
  from cobo_waas2.models.trigger_test_webhook_event_request import (
      TriggerTestWebhookEventRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersWebhooksApi(api_client)
      trigger_test_webhook_event_request = cobo_waas2.TriggerTestWebhookEventRequest(
          event_type="wallets.transaction.created"
      )

      try:
          # Trigger test event
          api_response = api_instance.trigger_test_webhook_event(
              trigger_test_webhook_event_request=trigger_test_webhook_event_request
          )
          print("The response of DevelopersWebhooksApi->trigger_test_webhook_event:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling DevelopersWebhooksApi->trigger_test_webhook_event: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersWebhooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersWebhooksApi apiInstance = new DevelopersWebhooksApi();
      TriggerTestWebhookEventRequest triggerTestWebhookEventRequest =
          new TriggerTestWebhookEventRequest()
              .eventType(WebhookEventType.WALLETS_TRANSACTION_CREATED);
      try {
        TriggerTestWebhookEvent201Response result =
            apiInstance.triggerTestWebhookEvent(triggerTestWebhookEventRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersWebhooksApi#triggerTestWebhookEvent");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	triggerTestWebhookEventRequest := *coboWaas2.NewTriggerTestWebhookEventRequest(coboWaas2.WebhookEventType("wallets.transaction.created"))

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersWebhooksAPI.TriggerTestWebhookEvent(ctx).
  		TriggerTestWebhookEventRequest(triggerTestWebhookEventRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersWebhooksAPI.TriggerTestWebhookEvent``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `TriggerTestWebhookEvent`: TriggerTestWebhookEvent201Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `DevelopersWebhooksAPI.TriggerTestWebhookEvent`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersWebhooksApi();
  const opts = {
    TriggerTestWebhookEventRequest:
      CoboWaas2.TriggerTestWebhookEventRequest.constructFromObject({
        event_type: "wallets.transaction.created",
      }),
  };
  apiInstance.triggerTestWebhookEvent(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Update webhook endpoint
Source: https://cobo.com/developers/v2/api-references/developers--webhooks/update-webhook-endpoint

put /webhooks/endpoints/{endpoint_id}
This operation updates the information of a specified webhook endpoint.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.update_webhook_endpoint_by_id_request import (
      UpdateWebhookEndpointByIdRequest,
  )
  from cobo_waas2.models.webhook_endpoint import WebhookEndpoint
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersWebhooksApi(api_client)
      endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      update_webhook_endpoint_by_id_request = (
          cobo_waas2.UpdateWebhookEndpointByIdRequest()
      )

      try:
          # Update webhook endpoint
          api_response = api_instance.update_webhook_endpoint_by_id(
              endpoint_id,
              update_webhook_endpoint_by_id_request=update_webhook_endpoint_by_id_request,
          )
          print("The response of DevelopersWebhooksApi->update_webhook_endpoint_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling DevelopersWebhooksApi->update_webhook_endpoint_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersWebhooksApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersWebhooksApi apiInstance = new DevelopersWebhooksApi();
      UUID endpointId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      UpdateWebhookEndpointByIdRequest updateWebhookEndpointByIdRequest =
          new UpdateWebhookEndpointByIdRequest();
      try {
        WebhookEndpoint result =
            apiInstance.updateWebhookEndpointById(endpointId, updateWebhookEndpointByIdRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersWebhooksApi#updateWebhookEndpointById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	endpointId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	updateWebhookEndpointByIdRequest := *coboWaas2.NewUpdateWebhookEndpointByIdRequest()

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersWebhooksAPI.UpdateWebhookEndpointById(ctx, endpointId).
  		UpdateWebhookEndpointByIdRequest(updateWebhookEndpointByIdRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersWebhooksAPI.UpdateWebhookEndpointById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UpdateWebhookEndpointById`: WebhookEndpoint
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `DevelopersWebhooksAPI.UpdateWebhookEndpointById`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersWebhooksApi();
  const endpoint_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    UpdateWebhookEndpointByIdRequest:
      new CoboWaas2.UpdateWebhookEndpointByIdRequest(),
  };
  apiInstance.updateWebhookEndpointById(endpoint_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get API key information
Source: https://cobo.com/developers/v2/api-references/developers/get-api-key-information

get /developers/api_key_info
This operation retrieves the details of the API key that you are using.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.get_api_key_info200_response import GetApiKeyInfo200Response
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersApi(api_client)

      try:
          # Get API key information
          api_response = api_instance.get_api_key_info()
          print("The response of DevelopersApi->get_api_key_info:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling DevelopersApi->get_api_key_info: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersApi apiInstance = new DevelopersApi();
      try {
        GetApiKeyInfo200Response result = apiInstance.getApiKeyInfo();
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersApi#getApiKeyInfo");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersAPI.GetApiKeyInfo(ctx).Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `DevelopersAPI.GetApiKeyInfo``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetApiKeyInfo`: GetApiKeyInfo200Response
  	fmt.Fprintf(os.Stdout, "Response from `DevelopersAPI.GetApiKeyInfo`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersApi();
  apiInstance.getApiKeyInfo().then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List all callback messages
Source: https://cobo.com/developers/v2/api-references/developers/list-all-callback-messages

get /developers/callback_messages
This operation retrieves all the callback messages in your organization.

For more details about how to respond to callback messages, refer to [Callback messages](https://www.cobo.com/developers/v2/guides/webhooks-callbacks/set-up-endpoint#callback-messages).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_callback_messages200_response import (
      ListCallbackMessages200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersApi(api_client)
      callback_message_ids = (
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479"
      )
      request_ids = (
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479"
      )
      transaction_ids = (
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479"
      )
      wallet_ids = (
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479"
      )
      status = "Approved"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List all callback messages
          api_response = api_instance.list_callback_messages(
              callback_message_ids=callback_message_ids,
              request_ids=request_ids,
              transaction_ids=transaction_ids,
              wallet_ids=wallet_ids,
              status=status,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of DevelopersApi->list_callback_messages:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling DevelopersApi->list_callback_messages: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersApi apiInstance = new DevelopersApi();
      String callbackMessageIds =
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479";
      String requestIds = "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479";
      String transactionIds =
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479";
      String walletIds = "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479";
      String status = "Denied";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListCallbackMessages200Response result =
            apiInstance.listCallbackMessages(
                callbackMessageIds,
                requestIds,
                transactionIds,
                walletIds,
                status,
                limit,
                before,
                after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersApi#listCallbackMessages");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	callbackMessageIds := "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	requestIds := "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	transactionIds := "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	walletIds := "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	status := "Approved"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersAPI.ListCallbackMessages(ctx).
  		CallbackMessageIds(callbackMessageIds).
  		RequestIds(requestIds).
  		TransactionIds(transactionIds).
  		WalletIds(walletIds).
  		Status(status).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersAPI.ListCallbackMessages``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListCallbackMessages`: ListCallbackMessages200Response
  	fmt.Fprintf(os.Stdout, "Response from `DevelopersAPI.ListCallbackMessages`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersApi();
  const opts = {
    callback_message_ids:
      "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479",
    request_ids:
      "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479",
    transaction_ids:
      "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479",
    wallet_ids:
      "f47ac10b-58cc-4372-a567-0e02b2c3d479,f47ac10b-58cc-4372-a567-0e02b2c3d479",
    status: "Approved",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listCallbackMessages(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Check Fee Station usage
Source: https://cobo.com/developers/v2/api-references/feestation/check-fee-station-usage

post /fee_station/check_fee_station_usage
This operation evaluates Fee Station usage for the current transaction. 

It determines whether Fee station can be used, checks if the Fee Station balance is sufficient, and returns a breakdown of the amounts involved, including any portion that must be covered by the user or sponsored in USD stablecoin.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.fee_station_check_fee_station_usage import (
      FeeStationCheckFeeStationUsage,
  )
  from cobo_waas2.models.fee_station_check_fee_station_usage_response import (
      FeeStationCheckFeeStationUsageResponse,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.FeeStationApi(api_client)
      fee_station_check_fee_station_usage = cobo_waas2.FeeStationCheckFeeStationUsage(
          request_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
          amount="100.5",
          token_id="ETH_USDT",
          estimated_fee_amount="0.0021",
          from_address="0x1234567890abcdef1234567890abcdef12345678",
          from_wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479"
      )

      try:
          # Check Fee Station usage
          api_response = api_instance.check_fee_station_usage(
              fee_station_check_fee_station_usage=fee_station_check_fee_station_usage
          )
          print("The response of FeeStationApi->check_fee_station_usage:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling FeeStationApi->check_fee_station_usage: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.FeeStationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      FeeStationApi apiInstance = new FeeStationApi();
      FeeStationCheckFeeStationUsage feeStationCheckFeeStationUsage =
          new FeeStationCheckFeeStationUsage();
      try {
        FeeStationCheckFeeStationUsageResponse result =
            apiInstance.checkFeeStationUsage(feeStationCheckFeeStationUsage);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling FeeStationApi#checkFeeStationUsage");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	feeStationCheckFeeStationUsage := *coboWaas2.NewFeeStationCheckFeeStationUsage("f47ac10b-58cc-4372-a567-0e02b2c3d479", "100.5", "ETH_USDT", "0.0021", "0x1234567890abcdef1234567890abcdef12345678", "f47ac10b-58cc-4372-a567-0e02b2c3d479")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.FeeStationAPI.CheckFeeStationUsage(ctx).
  		FeeStationCheckFeeStationUsage(feeStationCheckFeeStationUsage).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `FeeStationAPI.CheckFeeStationUsage``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CheckFeeStationUsage`: FeeStationCheckFeeStationUsageResponse
  	fmt.Fprintf(os.Stdout, "Response from `FeeStationAPI.CheckFeeStationUsage`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.FeeStationApi();
  const opts = {
    FeeStationCheckFeeStationUsage:
      new CoboWaas2.FeeStationCheckFeeStationUsage(),
  };
  apiInstance.checkFeeStationUsage(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get Fee Station transaction information
Source: https://cobo.com/developers/v2/api-references/feestation/get-fee-station-transaction-information

get /fee_station/transactions/{transaction_id}
This operation retrieves detailed information about a specified Fee Station transaction record, such as the transaction status, source address, destination address, and timestamp.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.transaction_detail import TransactionDetail
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.FeeStationApi(api_client)
      transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get Fee Station transaction information
          api_response = api_instance.get_fee_station_transaction_by_id(transaction_id)
          print("The response of FeeStationApi->get_fee_station_transaction_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling FeeStationApi->get_fee_station_transaction_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.FeeStationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      FeeStationApi apiInstance = new FeeStationApi();
      UUID transactionId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        TransactionDetail result = apiInstance.getFeeStationTransactionById(transactionId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling FeeStationApi#getFeeStationTransactionById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.FeeStationAPI.GetFeeStationTransactionById(ctx, transactionId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `FeeStationAPI.GetFeeStationTransactionById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetFeeStationTransactionById`: TransactionDetail
  	fmt.Fprintf(os.Stdout, "Response from `FeeStationAPI.GetFeeStationTransactionById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.FeeStationApi();
  const transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getFeeStationTransactionById(transaction_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List all Fee Station transactions
Source: https://cobo.com/developers/v2/api-references/feestation/list-all-fee-station-transactions

get /fee_station/transactions
This operation retrieves all Fee Station transactions under your organization.

You can filter the results by request ID, Cobo ID, transaction ID, transaction hash, type, status, and timestamp. You can also paginate and sort your query results.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_transactions200_response import ListTransactions200Response
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.FeeStationApi(api_client)
      request_id = "web_send_by_user_327_1610444045047"
      cobo_ids = "20231213122855000000000000000000,20231213122955000000000000000000"
      transaction_ids = (
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3"
      )
      transaction_hashes = (
          "239861be9a4afe080c359b7fe4a1d035945ec46256b1a0f44d1267c71de8ec28"
      )
      types = "Deposit,Withdrawal"
      statuses = "Completed,Failed"
      chain_ids = "BTC,ETH"
      token_ids = "ETH_USDT,ETH_USDC"
      asset_ids = "USDT,USDC"
      min_created_timestamp = 1635744000000
      max_created_timestamp = 1635744000000
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
      direction = "ASC"

      try:
          # List all Fee Station transactions
          api_response = api_instance.list_fee_station_transactions(
              request_id=request_id,
              cobo_ids=cobo_ids,
              transaction_ids=transaction_ids,
              transaction_hashes=transaction_hashes,
              types=types,
              statuses=statuses,
              chain_ids=chain_ids,
              token_ids=token_ids,
              asset_ids=asset_ids,
              min_created_timestamp=min_created_timestamp,
              max_created_timestamp=max_created_timestamp,
              limit=limit,
              before=before,
              after=after,
              direction=direction,
          )
          print("The response of FeeStationApi->list_fee_station_transactions:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling FeeStationApi->list_fee_station_transactions: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.FeeStationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      FeeStationApi apiInstance = new FeeStationApi();
      String requestId = "web_send_by_user_327_1610444045047";
      String coboIds = "20231213122855000000000000000000,20231213122955000000000000000000";
      String transactionIds =
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3";
      String transactionHashes = "239861be9a4afe080c359b7fe4a1d035945ec46256b1a0f44d1267c71de8ec28";
      String types = "Deposit,Withdrawal";
      String statuses = "Completed,Failed";
      String chainIds = "BTC,ETH";
      String tokenIds = "ETH_USDT,ETH_USDC";
      String assetIds = "USDT,USDC";
      Long minCreatedTimestamp = 1635744000000L;
      Long maxCreatedTimestamp = 1635744000000L;
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      String direction = "ASC";
      try {
        ListTransactions200Response result =
            apiInstance.listFeeStationTransactions(
                requestId,
                coboIds,
                transactionIds,
                transactionHashes,
                types,
                statuses,
                chainIds,
                tokenIds,
                assetIds,
                minCreatedTimestamp,
                maxCreatedTimestamp,
                limit,
                before,
                after,
                direction);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling FeeStationApi#listFeeStationTransactions");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	requestId := "web_send_by_user_327_1610444045047"
  	coboIds := "20231213122855000000000000000000,20231213122955000000000000000000"
  	transactionIds := "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3"
  	transactionHashes := "239861be9a4afe080c359b7fe4a1d035945ec46256b1a0f44d1267c71de8ec28"
  	types := "Deposit,Withdrawal"
  	statuses := "Completed,Failed"
  	chainIds := "BTC,ETH"
  	tokenIds := "ETH_USDT,ETH_USDC"
  	assetIds := "USDT,USDC"
  	minCreatedTimestamp := int64(1635744000000)
  	maxCreatedTimestamp := int64(1635744000000)
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
  	direction := "ASC"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.FeeStationAPI.ListFeeStationTransactions(ctx).
  		RequestId(requestId).
  		CoboIds(coboIds).
  		TransactionIds(transactionIds).
  		TransactionHashes(transactionHashes).
  		Types(types).
  		Statuses(statuses).
  		ChainIds(chainIds).
  		TokenIds(tokenIds).
  		AssetIds(assetIds).
  		MinCreatedTimestamp(minCreatedTimestamp).
  		MaxCreatedTimestamp(maxCreatedTimestamp).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Direction(direction).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `FeeStationAPI.ListFeeStationTransactions``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListFeeStationTransactions`: ListTransactions200Response
  	fmt.Fprintf(os.Stdout, "Response from `FeeStationAPI.ListFeeStationTransactions`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.FeeStationApi();
  const opts = {
    request_id: "web_send_by_user_327_1610444045047",
    cobo_ids: "20231213122855000000000000000000,20231213122955000000000000000000",
    transaction_ids:
      "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3",
    transaction_hashes:
      "239861be9a4afe080c359b7fe4a1d035945ec46256b1a0f44d1267c71de8ec28",
    types: "Deposit,Withdrawal",
    statuses: "Completed,Failed",
    chain_ids: "BTC,ETH",
    token_ids: "ETH_USDT,ETH_USDC",
    asset_ids: "USDT,USDC",
    min_created_timestamp: 1635744000000,
    max_created_timestamp: 1635744000000,
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
    direction: "ASC",
  };
  apiInstance.listFeeStationTransactions(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List Fee Station addresses
Source: https://cobo.com/developers/v2/api-references/feestation/list-fee-station-addresses

get /fee_station/addresses
This operation retrieves a list of deposit addresses of your Fee Station, including the chain ID, address, and additional information. You can filter the result by chain ID and address.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_addresses200_response import ListAddresses200Response
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.FeeStationApi(api_client)
      chain_ids = "BTC,ETH"
      addresses = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List Fee Station addresses
          api_response = api_instance.list_fee_station_addresses(
              chain_ids=chain_ids,
              addresses=addresses,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of FeeStationApi->list_fee_station_addresses:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling FeeStationApi->list_fee_station_addresses: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.FeeStationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      FeeStationApi apiInstance = new FeeStationApi();
      String chainIds = "BTC,ETH";
      String addresses =
          "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListAddresses200Response result =
            apiInstance.listFeeStationAddresses(chainIds, addresses, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling FeeStationApi#listFeeStationAddresses");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	chainIds := "BTC,ETH"
  	addresses := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.FeeStationAPI.ListFeeStationAddresses(ctx).
  		ChainIds(chainIds).
  		Addresses(addresses).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `FeeStationAPI.ListFeeStationAddresses``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListFeeStationAddresses`: ListAddresses200Response
  	fmt.Fprintf(os.Stdout, "Response from `FeeStationAPI.ListFeeStationAddresses`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.FeeStationApi();
  const opts = {
    chain_ids: "BTC,ETH",
    addresses:
      "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listFeeStationAddresses(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List Fee Station fiat transactions
Source: https://cobo.com/developers/v2/api-references/feestation/list-fee-station-fiat-transactions

get /fee_station/fiat_transactions
This operation retrieves all Fee Station fiat transactions under your organization.

You can filter the results by request IDs, transaction IDs, transaction type, and created timestamp. You can also paginate your query results.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.fee_station_fiat_transaction_type import (
      FeeStationFiatTransactionType,
  )
  from cobo_waas2.models.list_fee_station_fiat_transactions200_response import (
      ListFeeStationFiatTransactions200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.FeeStationApi(api_client)
      transaction_ids = (
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3"
      )
      transaction_type = cobo_waas2.FeeStationFiatTransactionType()
      min_created_timestamp = 1635744000000
      max_created_timestamp = 1635744000000
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
      limit = 10

      try:
          # List Fee Station fiat transactions
          api_response = api_instance.list_fee_station_fiat_transactions(
              transaction_ids=transaction_ids,
              transaction_type=transaction_type,
              min_created_timestamp=min_created_timestamp,
              max_created_timestamp=max_created_timestamp,
              before=before,
              after=after,
              limit=limit,
          )
          print("The response of FeeStationApi->list_fee_station_fiat_transactions:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling FeeStationApi->list_fee_station_fiat_transactions: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.FeeStationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      FeeStationApi apiInstance = new FeeStationApi();
      String transactionIds =
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3";
      FeeStationFiatTransactionType transactionType =
          FeeStationFiatTransactionType.fromValue("deposit");
      Long minCreatedTimestamp = 1635744000000L;
      Long maxCreatedTimestamp = 1635744000000L;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      Integer limit = 10;
      try {
        ListFeeStationFiatTransactions200Response result =
            apiInstance.listFeeStationFiatTransactions(
                transactionIds,
                transactionType,
                minCreatedTimestamp,
                maxCreatedTimestamp,
                before,
                after,
                limit);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling FeeStationApi#listFeeStationFiatTransactions");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionIds := "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3"
  	transactionType := coboWaas2.FeeStationFiatTransactionType("deposit")
  	minCreatedTimestamp := int64(1635744000000)
  	maxCreatedTimestamp := int64(1635744000000)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
  	limit := int32(10)

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.FeeStationAPI.ListFeeStationFiatTransactions(ctx).
  		TransactionIds(transactionIds).
  		TransactionType(transactionType).
  		MinCreatedTimestamp(minCreatedTimestamp).
  		MaxCreatedTimestamp(maxCreatedTimestamp).
  		Before(before).
  		After(after).
  		Limit(limit).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `FeeStationAPI.ListFeeStationFiatTransactions``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListFeeStationFiatTransactions`: ListFeeStationFiatTransactions200Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `FeeStationAPI.ListFeeStationFiatTransactions`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.FeeStationApi();
  const opts = {
    transaction_ids:
      "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3",
    transaction_type: new CoboWaas2.FeeStationFiatTransactionType(),
    min_created_timestamp: 1635744000000,
    max_created_timestamp: 1635744000000,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
    limit: 10,
  };
  apiInstance.listFeeStationFiatTransactions(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List Fee Station token balances
Source: https://cobo.com/developers/v2/api-references/feestation/list-fee-station-token-balances

get /fee_station/tokens
The operation retrieves a list of token balances within your Fee Station.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_token_balances_for_fee_station200_response import (
      ListTokenBalancesForFeeStation200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.FeeStationApi(api_client)
      token_ids = "ETH_USDT,ETH_USDC"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List Fee Station token balances
          api_response = api_instance.list_token_balances_for_fee_station(
              token_ids=token_ids, limit=limit, before=before, after=after
          )
          print("The response of FeeStationApi->list_token_balances_for_fee_station:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling FeeStationApi->list_token_balances_for_fee_station: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.FeeStationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      FeeStationApi apiInstance = new FeeStationApi();
      String tokenIds = "ETH_USDT,ETH_USDC";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListTokenBalancesForFeeStation200Response result =
            apiInstance.listTokenBalancesForFeeStation(tokenIds, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling FeeStationApi#listTokenBalancesForFeeStation");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenIds := "ETH_USDT,ETH_USDC"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.FeeStationAPI.ListTokenBalancesForFeeStation(ctx).
  		TokenIds(tokenIds).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `FeeStationAPI.ListTokenBalancesForFeeStation``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTokenBalancesForFeeStation`: ListTokenBalancesForFeeStation200Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `FeeStationAPI.ListTokenBalancesForFeeStation`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.FeeStationApi();
  const opts = {
    token_ids: "ETH_USDT,ETH_USDC",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listTokenBalancesForFeeStation(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get Org Access Token
Source: https://cobo.com/developers/v2/api-references/oauth/get-org-access-token

get /oauth/token
<Note>This operation is only applicable to Cobo Portal App developers. To call this operation, you need to use the Cobo OAuth authentication method that requires an app key.</Note>
This operation allows Cobo Portal Apps to get an Org Access Token and a Refresh Token with a specified client ID, organization ID, and grant type. 

Access tokens allow the app to signal to the WaaS service that it has received permission to access specific resources of the app user's [organization](https://manuals.cobo.com/en/portal/organization/introduction). Once the app has been granted permission by the organization's admin, it can use this operation to obtain both an Org Access Token and a Refresh Token.

For security purposes, Org Access Tokens expire after a certain period. Once they expire, the app needs to call [Refresh token](https://www.cobo.com/developers/v2/api-references/oauth/refresh-org-access-token) to get a new Org Access Token and a new Refresh Token. 


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.get_token2_xx_response import GetToken2XXResponse
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.OAuthApi(api_client)
      client_id = "pvSwS8iFrfK0oZrB0ugG54XPDOLEv0Ij"
      org_id = "e3986401-4aec-480a-973d-e775a4518413"
      grant_type = "org_implicit"

      try:
          # Get Org Access Token
          api_response = api_instance.get_token(client_id, org_id, grant_type)
          print("The response of OAuthApi->get_token:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling OAuthApi->get_token: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.OAuthApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      OAuthApi apiInstance = new OAuthApi();
      String clientId = "pvSwS8iFrfK0oZrB0ugG54XPDOLEv0Ij";
      String orgId = "e3986401-4aec-480a-973d-e775a4518413";
      String grantType = "org_implicit";
      try {
        GetToken2XXResponse result = apiInstance.getToken(clientId, orgId, grantType);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling OAuthApi#getToken");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	clientId := "pvSwS8iFrfK0oZrB0ugG54XPDOLEv0Ij"
  	orgId := "e3986401-4aec-480a-973d-e775a4518413"
  	grantType := "org_implicit"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.OAuthAPI.GetToken(ctx).
  		ClientId(clientId).
  		OrgId(orgId).
  		GrantType(grantType).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `OAuthAPI.GetToken``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetToken`: GetToken2XXResponse
  	fmt.Fprintf(os.Stdout, "Response from `OAuthAPI.GetToken`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.OAuthApi();
  const client_id = "pvSwS8iFrfK0oZrB0ugG54XPDOLEv0Ij";
  const org_id = "e3986401-4aec-480a-973d-e775a4518413";
  const grant_type = "org_implicit";
  apiInstance.getToken(client_id, org_id, grant_type).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Refresh Org Access Token
Source: https://cobo.com/developers/v2/api-references/oauth/refresh-org-access-token

post /oauth/token
<Note>This operation is only applicable to Cobo Portal Apps developers. To call this operation, you need to use the Cobo OAuth authentication method that requires an app key.</Note>
This operation allows Cobo Portal Apps to obtain a new Org Access Token with a specified client ID, grant type and a Refresh Token. 

For security purposes, Org Access Tokens expire after a certain period. Once they expire, the app needs to call this operation to get a new Org Access Token and a new Refresh Token. 


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.refresh_token2_xx_response import RefreshToken2XXResponse
  from cobo_waas2.models.refresh_token_request import RefreshTokenRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.OAuthApi(api_client)
      refresh_token_request = cobo_waas2.RefreshTokenRequest()

      try:
          # Refresh Org Access Token
          api_response = api_instance.refresh_token(refresh_token_request)
          print("The response of OAuthApi->refresh_token:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling OAuthApi->refresh_token: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.OAuthApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      OAuthApi apiInstance = new OAuthApi();
      RefreshTokenRequest refreshTokenRequest = new RefreshTokenRequest();
      try {
        RefreshToken2XXResponse result = apiInstance.refreshToken(refreshTokenRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling OAuthApi#refreshToken");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	refreshTokenRequest := *coboWaas2.NewRefreshTokenRequest()

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.OAuthAPI.RefreshToken(ctx).
  		RefreshTokenRequest(refreshTokenRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `OAuthAPI.RefreshToken``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `RefreshToken`: RefreshToken2XXResponse
  	fmt.Fprintf(os.Stdout, "Response from `OAuthAPI.RefreshToken`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.OAuthApi();
  const RefreshTokenRequest = new CoboWaas2.RefreshTokenRequest();
  apiInstance.refreshToken(RefreshTokenRequest).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get organization information
Source: https://cobo.com/developers/v2/api-references/organizations/get-organization-information

get /organizations/info
This operation retrieves the detailed information about the organization associated with the current API key.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.org_info import OrgInfo
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.OrganizationsApi(api_client)

      try:
          # Get organization information
          api_response = api_instance.get_org_info()
          print("The response of OrganizationsApi->get_org_info:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling OrganizationsApi->get_org_info: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.OrganizationsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      OrganizationsApi apiInstance = new OrganizationsApi();
      try {
        OrgInfo result = apiInstance.getOrgInfo();
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling OrganizationsApi#getOrgInfo");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.OrganizationsAPI.GetOrgInfo(ctx).Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `OrganizationsAPI.GetOrgInfo``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetOrgInfo`: OrgInfo
  	fmt.Fprintf(os.Stdout, "Response from `OrganizationsAPI.GetOrgInfo`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.OrganizationsApi();
  apiInstance.getOrgInfo().then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create claim activity
Source: https://cobo.com/developers/v2/api-references/stakings/create-claim-activity

post /stakings/activities/claim
This operation creates a claim request.

<Note>Currently, only the Ethereum Beacon protocol supports this operation.</Note>

For some protocols, you can use the `fee` property in the request body to specify the maximum fee you are willing to pay. The transaction will fail if the actual fee exceeds the specified maximum fee. 


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_claim_activity_request import CreateClaimActivityRequest
  from cobo_waas2.models.create_stake_activity201_response import (
      CreateStakeActivity201Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      create_claim_activity_request = cobo_waas2.CreateClaimActivityRequest(
          staking_id="f47ac10b-58cc-4372-a567-0e02b2c3d479"
      )

      try:
          # Create claim activity
          api_response = api_instance.create_claim_activity(
              create_claim_activity_request=create_claim_activity_request
          )
          print("The response of StakingsApi->create_claim_activity:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling StakingsApi->create_claim_activity: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      CreateClaimActivityRequest createClaimActivityRequest =
          new CreateClaimActivityRequest().stakingId("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        CreateStakeActivity201Response result =
            apiInstance.createClaimActivity(createClaimActivityRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#createClaimActivity");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createClaimActivityRequest := *coboWaas2.NewCreateClaimActivityRequest("f47ac10b-58cc-4372-a567-0e02b2c3d479")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.CreateClaimActivity(ctx).
  		CreateClaimActivityRequest(createClaimActivityRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `StakingsAPI.CreateClaimActivity``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateClaimActivity`: CreateStakeActivity201Response
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.CreateClaimActivity`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    CreateClaimActivityRequest:
      CoboWaas2.CreateClaimActivityRequest.constructFromObject({
        staking_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
      }),
  };
  apiInstance.createClaimActivity(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create stake activity
Source: https://cobo.com/developers/v2/api-references/stakings/create-stake-activity

post /stakings/activities/stake
This operation creates a staking request.

For some protocols, you can use the `fee` property in the request body to specify the maximum fee you are willing to pay. The transaction will fail if the actual fee exceeds the specified maximum fee. 

<Note>For the Babylon protocol, you can only select UTXO as the fee model.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_stake_activity201_response import (
      CreateStakeActivity201Response,
  )
  from cobo_waas2.models.create_stake_activity_request import CreateStakeActivityRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      create_stake_activity_request = cobo_waas2.CreateStakeActivityRequest(
          pool_id="babylon_btc_signet",
          amount="100.00",
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          ),
      )

      try:
          # Create stake activity
          api_response = api_instance.create_stake_activity(
              create_stake_activity_request=create_stake_activity_request
          )
          print("The response of StakingsApi->create_stake_activity:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling StakingsApi->create_stake_activity: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      CreateStakeActivityRequest createStakeActivityRequest =
          new CreateStakeActivityRequest()
              .poolId(StakingPoolId.BABYLON_BTC_SIGNET)
              .amount("100.00")
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        CreateStakeActivity201Response result =
            apiInstance.createStakeActivity(createStakeActivityRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#createStakeActivity");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createStakeActivityRequest := *coboWaas2.NewCreateStakeActivityRequest(coboWaas2.StakingPoolId("babylon_btc_signet"), "100.00", coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.CreateStakeActivity(ctx).
  		CreateStakeActivityRequest(createStakeActivityRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `StakingsAPI.CreateStakeActivity``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateStakeActivity`: CreateStakeActivity201Response
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.CreateStakeActivity`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    CreateStakeActivityRequest:
      CoboWaas2.CreateStakeActivityRequest.constructFromObject({
        pool_id: "babylon_btc_signet",
        amount: "100.00",
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
      }),
  };
  apiInstance.createStakeActivity(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create unstake activity
Source: https://cobo.com/developers/v2/api-references/stakings/create-unstake-activity

post /stakings/activities/unstake
This operation creates an unstaking request. Your staked tokens will be automatically unlocked once the specified locking period ends. If you want to withdraw your tokens beforehand, you can unstake them with this operation.

For some protocols, you can use the `fee` property in the request body to specify the maximum fee you are willing to pay. The transaction will fail if the actual fee exceeds the specified maximum fee. 

<Note>For the Babylon protocol, you can only select UTXO as the fee model.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_stake_activity201_response import (
      CreateStakeActivity201Response,
  )
  from cobo_waas2.models.create_unstake_activity_request import (
      CreateUnstakeActivityRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      create_unstake_activity_request = cobo_waas2.CreateUnstakeActivityRequest(
          staking_id="0011039d-27fb-49ba-b172-6e0aa80e37ec"
      )

      try:
          # Create unstake activity
          api_response = api_instance.create_unstake_activity(
              create_unstake_activity_request=create_unstake_activity_request
          )
          print("The response of StakingsApi->create_unstake_activity:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling StakingsApi->create_unstake_activity: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      CreateUnstakeActivityRequest createUnstakeActivityRequest =
          new CreateUnstakeActivityRequest().stakingId("0011039d-27fb-49ba-b172-6e0aa80e37ec");
      try {
        CreateStakeActivity201Response result =
            apiInstance.createUnstakeActivity(createUnstakeActivityRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#createUnstakeActivity");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createUnstakeActivityRequest := *coboWaas2.NewCreateUnstakeActivityRequest("0011039d-27fb-49ba-b172-6e0aa80e37ec")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.CreateUnstakeActivity(ctx).
  		CreateUnstakeActivityRequest(createUnstakeActivityRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `StakingsAPI.CreateUnstakeActivity``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateUnstakeActivity`: CreateStakeActivity201Response
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.CreateUnstakeActivity`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    CreateUnstakeActivityRequest:
      CoboWaas2.CreateUnstakeActivityRequest.constructFromObject({
        staking_id: "0011039d-27fb-49ba-b172-6e0aa80e37ec",
      }),
  };
  apiInstance.createUnstakeActivity(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create withdraw activity
Source: https://cobo.com/developers/v2/api-references/stakings/create-withdraw-activity

post /stakings/activities/withdraw
This operation creates a withdrawal request. 

For some protocols, you can use the `fee` property in the request body to specify the maximum fee you are willing to pay. The transaction will fail if the actual fee exceeds the specified maximum fee. 

<Note>For the Babylon protocol, you can only select UTXO as the fee model.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_stake_activity201_response import (
      CreateStakeActivity201Response,
  )
  from cobo_waas2.models.create_withdraw_activity_request import (
      CreateWithdrawActivityRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      create_withdraw_activity_request = cobo_waas2.CreateWithdrawActivityRequest(
          staking_id="0011039d-27fb-49ba-b172-6e0aa80e37ec",
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          ),
      )

      try:
          # Create withdraw activity
          api_response = api_instance.create_withdraw_activity(
              create_withdraw_activity_request=create_withdraw_activity_request
          )
          print("The response of StakingsApi->create_withdraw_activity:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling StakingsApi->create_withdraw_activity: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      CreateWithdrawActivityRequest createWithdrawActivityRequest =
          new CreateWithdrawActivityRequest()
              .stakingId("0011039d-27fb-49ba-b172-6e0aa80e37ec")
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        CreateStakeActivity201Response result =
            apiInstance.createWithdrawActivity(createWithdrawActivityRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#createWithdrawActivity");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createWithdrawActivityRequest := *coboWaas2.NewCreateWithdrawActivityRequest("0011039d-27fb-49ba-b172-6e0aa80e37ec", coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.CreateWithdrawActivity(ctx).
  		CreateWithdrawActivityRequest(createWithdrawActivityRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.CreateWithdrawActivity``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateWithdrawActivity`: CreateStakeActivity201Response
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.CreateWithdrawActivity`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    CreateWithdrawActivityRequest:
      CoboWaas2.CreateWithdrawActivityRequest.constructFromObject({
        staking_id: "0011039d-27fb-49ba-b172-6e0aa80e37ec",
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
      }),
  };
  apiInstance.createWithdrawActivity(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Estimate staking fees v2
Source: https://cobo.com/developers/v2/api-references/stakings/estimate-staking-fees-v2

post /stakings/estimate_fee_v2
This operation calculates the fee required for a staking activity based on factors such as network congestion and transaction complexity.

<Note>For the Babylon protocol, you can only select UTXO as the fee model.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.eth_stake_estimated_fee import EthStakeEstimatedFee
  from cobo_waas2.models.get_staking_estimation_fee_request import (
      GetStakingEstimationFeeRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      get_staking_estimation_fee_request = cobo_waas2.GetStakingEstimationFeeRequest(
          activity_type="Stake",
          pool_id="babylon_btc_signet",
          amount="100.00",
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          ),
      )

      try:
          # Estimate staking fees v2
          api_response = api_instance.get_staking_estimation_fee_v2(
              get_staking_estimation_fee_request=get_staking_estimation_fee_request
          )
          print("The response of StakingsApi->get_staking_estimation_fee_v2:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling StakingsApi->get_staking_estimation_fee_v2: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      GetStakingEstimationFeeRequest getStakingEstimationFeeRequest =
          new GetStakingEstimationFeeRequest()
              .activityType(ActivityType.STAKE)
              .poolId(StakingPoolId.BABYLON_BTC_SIGNET)
              .amount("100.00")
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        EthStakeEstimatedFee result =
            apiInstance.getStakingEstimationFeeV2(getStakingEstimationFeeRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#getStakingEstimationFeeV2");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	getStakingEstimationFeeRequest := coboWaas2.get_staking_estimation_fee_request{
  		EstimateClaimFee: coboWaas2.NewEstimateClaimFee(coboWaas2.ActivityType("Stake")),
  	}

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.GetStakingEstimationFeeV2(ctx).
  		GetStakingEstimationFeeRequest(getStakingEstimationFeeRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.GetStakingEstimationFeeV2``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetStakingEstimationFeeV2`: EthStakeEstimatedFee
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.GetStakingEstimationFeeV2`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    GetStakingEstimationFeeRequest:
      CoboWaas2.GetStakingEstimationFeeRequest.constructFromObject({
        activity_type: "Stake",
        pool_id: "babylon_btc_signet",
        amount: "100.00",
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
      }),
  };
  apiInstance.getStakingEstimationFeeV2(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Expand Babylon BTC staking
Source: https://cobo.com/developers/v2/api-references/stakings/expand-babylon-btc-staking

post /stakings/protocols/babylon/stakings/expansions
This operation initiates a Babylon BTC staking expansion request. 

Before calling this operation, please ensure the following:
- The BTC staking position is active.
- The finality provider public keys are valid. Each BSN chain can have at most one finality provider public key.

The system first checks whether the provided BTC staking position is active. If active, it creates a new BTC staking position for the Phase-3 expansion.

The expansion is processed asynchronously and may take some time to complete.

For more information, refer to [Babylon's official doc](https://github.com/babylonlabs-io/babylon/tree/main/docs).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.babylon_create_staking_expansion import (
      BabylonCreateStakingExpansion,
  )
  from cobo_waas2.models.stakings import Stakings
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      babylon_create_staking_expansion = cobo_waas2.BabylonCreateStakingExpansion(
          staking_id="3f2840ce-44eb-450b-aa81-d3f84b772efb",
          finality_provider_public_keys=[
              "eca1b104dce16c30705f4147a9c4a373ac88646c5d1bcda6a89c018940cb96a0"
          ],
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          ),
      )

      try:
          # Expand Babylon BTC staking
          api_response = api_instance.create_babylon_staking_expansion(
              babylon_create_staking_expansion=babylon_create_staking_expansion
          )
          print("The response of StakingsApi->create_babylon_staking_expansion:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling StakingsApi->create_babylon_staking_expansion: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      BabylonCreateStakingExpansion babylonCreateStakingExpansion =
          new BabylonCreateStakingExpansion()
              .stakingId("3f2840ce-44eb-450b-aa81-d3f84b772efb")
              .finalityProviderPublicKeys(
                  Arrays.asList("eca1b104dce16c30705f4147a9c4a373ac88646c5d1bcda6a89c018940cb96a0"))
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        Stakings result = apiInstance.createBabylonStakingExpansion(babylonCreateStakingExpansion);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#createBabylonStakingExpansion");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	babylonCreateStakingExpansion := *coboWaas2.NewBabylonCreateStakingExpansion("3f2840ce-44eb-450b-aa81-d3f84b772efb", []string{"eca1b104dce16c30705f4147a9c4a373ac88646c5d1bcda6a89c018940cb96a0"}, coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.CreateBabylonStakingExpansion(ctx).
  		BabylonCreateStakingExpansion(babylonCreateStakingExpansion).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.CreateBabylonStakingExpansion``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateBabylonStakingExpansion`: Stakings
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.CreateBabylonStakingExpansion`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    BabylonCreateStakingExpansion:
      CoboWaas2.BabylonCreateStakingExpansion.constructFromObject({
        staking_id: "3f2840ce-44eb-450b-aa81-d3f84b772efb",
        finality_provider_public_keys: [
          "eca1b104dce16c30705f4147a9c4a373ac88646c5d1bcda6a89c018940cb96a0",
        ],
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
      }),
  };
  apiInstance.createBabylonStakingExpansion(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get Babylon airdrop registration details
Source: https://cobo.com/developers/v2/api-references/stakings/get-babylon-airdrop-registration-details

get /stakings/protocols/babylon/airdrops/registrations/{registration_id}
This operation returns the details of a specific Babylon airdrop registration, including registration status, Bitcoin (BTC) and Babylon addresses, airdrop amount, and error messages (if any).

Please note that registration is an asynchronous process and may take several minutes to complete. It is recommended to call this operation at regular intervals to track the status.

If the registration request fails, please check the error message and resolve the issues before resubmitting the registration request.

For more information, refer to [Babylon's official doc](https://github.com/babylonlabs-io/babylon/tree/main/docs).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.babylon_airdrop_registration import BabylonAirdropRegistration
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      registration_id = "registration_id_example"

      try:
          # Get Babylon airdrop registration details
          api_response = api_instance.get_babylon_airdrop_registration_by_id(
              registration_id
          )
          print("The response of StakingsApi->get_babylon_airdrop_registration_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling StakingsApi->get_babylon_airdrop_registration_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String registrationId = "registrationId_example";
      try {
        BabylonAirdropRegistration result =
            apiInstance.getBabylonAirdropRegistrationById(registrationId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#getBabylonAirdropRegistrationById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	registrationId := "registrationId_example"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.GetBabylonAirdropRegistrationById(ctx, registrationId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.GetBabylonAirdropRegistrationById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetBabylonAirdropRegistrationById`: BabylonAirdropRegistration
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `StakingsAPI.GetBabylonAirdropRegistrationById`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const registration_id = "registration_id_example";
  apiInstance.getBabylonAirdropRegistrationById(registration_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get Babylon Phase-2 registration details
Source: https://cobo.com/developers/v2/api-references/stakings/get-babylon-phase-2-registration-details

get /stakings/protocols/babylon/stakings/registrations/{registration_id}
This operation returns the details of a specific Babylon Phase-2 registration, including registration status, Bitcoin (BTC) and Babylon addresses, staked amount, and error messages (if any).

Please note that registration is an asynchronous process and may take several minutes to complete. It is recommended to call this operation at regular intervals to track the status.

If the registration request fails, please check the error message and resolve the issues before resubmitting the registration request.

For more information, refer to [Babylon's official doc](https://github.com/babylonlabs-io/babylon/tree/main/docs).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.babylon_staking_registration import BabylonStakingRegistration
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      registration_id = "registration_id_example"

      try:
          # Get Babylon Phase-2 registration details
          api_response = api_instance.get_babylon_staking_registration_by_id(
              registration_id
          )
          print("The response of StakingsApi->get_babylon_staking_registration_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling StakingsApi->get_babylon_staking_registration_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String registrationId = "registrationId_example";
      try {
        BabylonStakingRegistration result =
            apiInstance.getBabylonStakingRegistrationById(registrationId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#getBabylonStakingRegistrationById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	registrationId := "registrationId_example"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.GetBabylonStakingRegistrationById(ctx, registrationId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.GetBabylonStakingRegistrationById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetBabylonStakingRegistrationById`: BabylonStakingRegistration
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `StakingsAPI.GetBabylonStakingRegistrationById`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const registration_id = "registration_id_example";
  apiInstance.getBabylonStakingRegistrationById(registration_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get staking activity details
Source: https://cobo.com/developers/v2/api-references/stakings/get-staking-activity-details

get /stakings/activities/{activity_id}
This operation retrieves the details of a specified staking activity.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.activity import Activity
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      activity_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get staking activity details
          api_response = api_instance.get_staking_activity_by_id(activity_id)
          print("The response of StakingsApi->get_staking_activity_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling StakingsApi->get_staking_activity_by_id: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String activityId = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
      try {
        Activity result = apiInstance.getStakingActivityById(activityId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#getStakingActivityById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	activityId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.GetStakingActivityById(ctx, activityId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.GetStakingActivityById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetStakingActivityById`: Activity
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.GetStakingActivityById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const activity_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getStakingActivityById(activity_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get staking pool details
Source: https://cobo.com/developers/v2/api-references/stakings/get-staking-pool-details

get /stakings/pools/{pool_id}
This operation retrieves the detailed information about a specified staking pool.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.pool_details import PoolDetails
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      pool_id = "babylon_btc"

      try:
          # Get staking pool details
          api_response = api_instance.get_staking_pool_by_id(pool_id)
          print("The response of StakingsApi->get_staking_pool_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling StakingsApi->get_staking_pool_by_id: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String poolId = "babylon_btc";
      try {
        PoolDetails result = apiInstance.getStakingPoolById(poolId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#getStakingPoolById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	poolId := "babylon_btc"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.GetStakingPoolById(ctx, poolId).Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `StakingsAPI.GetStakingPoolById``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetStakingPoolById`: PoolDetails
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.GetStakingPoolById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const pool_id = "babylon_btc";
  apiInstance.getStakingPoolById(pool_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get staking position details
Source: https://cobo.com/developers/v2/api-references/stakings/get-staking-position-details

get /stakings/{staking_id}
This operation retrieves the detailed information about a specified staking position.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.stakings import Stakings
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      staking_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get staking position details
          api_response = api_instance.get_staking_by_id(staking_id)
          print("The response of StakingsApi->get_staking_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling StakingsApi->get_staking_by_id: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String stakingId = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
      try {
        Stakings result = apiInstance.getStakingById(stakingId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#getStakingById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	stakingId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.GetStakingById(ctx, stakingId).Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `StakingsAPI.GetStakingById``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetStakingById`: Stakings
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.GetStakingById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const staking_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getStakingById(staking_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List Babylon airdrop registrations
Source: https://cobo.com/developers/v2/api-references/stakings/list-babylon-airdrop-registrations

get /stakings/protocols/babylon/airdrops/registrations
This operation lists all Babylon airdrop registration records within your organization. You can filter the results by request status and Bitcoin (BTC) address.

The registration is processed asynchronously and may take some time to complete. It is recommended to implement automatic monitoring and handle the registration on time.

If the registration request fails, please check the error message and resolve the issues before resubmitting the registration request.

For more information, refer to [Babylon's official doc](https://github.com/babylonlabs-io/babylon/tree/main/docs).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_babylon_airdrop_registrations200_response import (
      ListBabylonAirdropRegistrations200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      status = "Processing"
      btc_address = "1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List Babylon airdrop registrations
          api_response = api_instance.list_babylon_airdrop_registrations(
              status=status,
              btc_address=btc_address,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of StakingsApi->list_babylon_airdrop_registrations:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling StakingsApi->list_babylon_airdrop_registrations: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String status = "Processing";
      String btcAddress = "1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListBabylonAirdropRegistrations200Response result =
            apiInstance.listBabylonAirdropRegistrations(status, btcAddress, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#listBabylonAirdropRegistrations");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	status := "Processing"
  	btcAddress := "1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.ListBabylonAirdropRegistrations(ctx).
  		Status(status).
  		BtcAddress(btcAddress).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.ListBabylonAirdropRegistrations``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListBabylonAirdropRegistrations`: ListBabylonAirdropRegistrations200Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `StakingsAPI.ListBabylonAirdropRegistrations`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    status: "Processing",
    btc_address: "1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listBabylonAirdropRegistrations(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List Babylon Phase-2 registrations
Source: https://cobo.com/developers/v2/api-references/stakings/list-babylon-phase-2-registrations

get /stakings/protocols/babylon/stakings/registrations
This operation lists all Babylon Phase-2 registration records within your organization. You can filter the results by request status and staking position ID.

The registration is processed asynchronously and may take some time to complete. It is recommended to implement automatic monitoring and handle the registration on time.

If the registration request fails, please check the error message and resolve the issues before resubmitting the registration request.

For more information, refer to [Babylon's official doc](https://github.com/babylonlabs-io/babylon/tree/main/docs).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_babylon_staking_registrations200_response import (
      ListBabylonStakingRegistrations200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      status = "Processing"
      staking_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List Babylon Phase-2 registrations
          api_response = api_instance.list_babylon_staking_registrations(
              status=status,
              staking_id=staking_id,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of StakingsApi->list_babylon_staking_registrations:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling StakingsApi->list_babylon_staking_registrations: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String status = "Processing";
      String stakingId = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListBabylonStakingRegistrations200Response result =
            apiInstance.listBabylonStakingRegistrations(status, stakingId, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#listBabylonStakingRegistrations");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	status := "Processing"
  	stakingId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.ListBabylonStakingRegistrations(ctx).
  		Status(status).
  		StakingId(stakingId).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.ListBabylonStakingRegistrations``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListBabylonStakingRegistrations`: ListBabylonStakingRegistrations200Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `StakingsAPI.ListBabylonStakingRegistrations`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    status: "Processing",
    staking_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listBabylonStakingRegistrations(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List staking activities
Source: https://cobo.com/developers/v2/api-references/stakings/list-staking-activities

get /stakings/activities
This operation retrieves a list of staking activities.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.activity_status import ActivityStatus
  from cobo_waas2.models.activity_type import ActivityType
  from cobo_waas2.models.list_staking_activities200_response import (
      ListStakingActivities200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      pool_id = "babylon_btc"
      staking_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      activity_type = cobo_waas2.ActivityType()
      activity_status = cobo_waas2.ActivityStatus()
      min_modified_timestamp = 1635744000000
      max_modified_timestamp = 1635744000000
      initiator = "steve@example.com"
      request_id = "web_send_by_user_327_1610444045047"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List staking activities
          api_response = api_instance.list_staking_activities(
              pool_id=pool_id,
              staking_id=staking_id,
              activity_type=activity_type,
              activity_status=activity_status,
              min_modified_timestamp=min_modified_timestamp,
              max_modified_timestamp=max_modified_timestamp,
              initiator=initiator,
              request_id=request_id,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of StakingsApi->list_staking_activities:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling StakingsApi->list_staking_activities: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String poolId = "babylon_btc";
      String stakingId = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
      ActivityType activityType = ActivityType.fromValue("Stake");
      ActivityStatus activityStatus = ActivityStatus.fromValue("Success");
      Long minModifiedTimestamp = 1635744000000L;
      Long maxModifiedTimestamp = 1635744000000L;
      String initiator = "steve@example.com";
      String requestId = "web_send_by_user_327_1610444045047";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListStakingActivities200Response result =
            apiInstance.listStakingActivities(
                poolId,
                stakingId,
                activityType,
                activityStatus,
                minModifiedTimestamp,
                maxModifiedTimestamp,
                initiator,
                requestId,
                limit,
                before,
                after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#listStakingActivities");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	poolId := "babylon_btc"
  	stakingId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	activityType := coboWaas2.ActivityType("Stake")
  	activityStatus := coboWaas2.ActivityStatus("Success")
  	minModifiedTimestamp := int64(1635744000000)
  	maxModifiedTimestamp := int64(1635744000000)
  	initiator := "steve@example.com"
  	requestId := "web_send_by_user_327_1610444045047"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.ListStakingActivities(ctx).
  		PoolId(poolId).
  		StakingId(stakingId).
  		ActivityType(activityType).
  		ActivityStatus(activityStatus).
  		MinModifiedTimestamp(minModifiedTimestamp).
  		MaxModifiedTimestamp(maxModifiedTimestamp).
  		Initiator(initiator).
  		RequestId(requestId).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `StakingsAPI.ListStakingActivities``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListStakingActivities`: ListStakingActivities200Response
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.ListStakingActivities`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    pool_id: "babylon_btc",
    staking_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
    activity_type: new CoboWaas2.ActivityType(),
    activity_status: new CoboWaas2.ActivityStatus(),
    min_modified_timestamp: 1635744000000,
    max_modified_timestamp: 1635744000000,
    initiator: "steve@example.com",
    request_id: "web_send_by_user_327_1610444045047",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listStakingActivities(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List staking pools
Source: https://cobo.com/developers/v2/api-references/stakings/list-staking-pools

get /stakings/pools
This operation retrieves a list of staking pools currently supported.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_staking_pools200_response import ListStakingPools200Response
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      chain_id = "ETH"
      token_id = "ETH_USDT"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List staking pools
          api_response = api_instance.list_staking_pools(
              chain_id=chain_id,
              token_id=token_id,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of StakingsApi->list_staking_pools:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling StakingsApi->list_staking_pools: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String chainId = "ETH";
      String tokenId = "ETH_USDT";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListStakingPools200Response result =
            apiInstance.listStakingPools(chainId, tokenId, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#listStakingPools");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	chainId := "ETH"
  	tokenId := "ETH_USDT"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.ListStakingPools(ctx).
  		ChainId(chainId).
  		TokenId(tokenId).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `StakingsAPI.ListStakingPools``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListStakingPools`: ListStakingPools200Response
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.ListStakingPools`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    chain_id: "ETH",
    token_id: "ETH_USDT",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listStakingPools(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List staking positions
Source: https://cobo.com/developers/v2/api-references/stakings/list-staking-positions

get /stakings
This operation retrieves a list of staking positions. 


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_stakings200_response import ListStakings200Response
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      pool_id = "babylon_btc"
      statuses = "Active,StakeInProgress,"
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      token_id = "ETH_USDT"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List staking positions
          api_response = api_instance.list_stakings(
              pool_id=pool_id,
              statuses=statuses,
              wallet_id=wallet_id,
              token_id=token_id,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of StakingsApi->list_stakings:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling StakingsApi->list_stakings: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String poolId = "babylon_btc";
      String statuses = "Active,StakeInProgress,";
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String tokenId = "ETH_USDT";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListStakings200Response result =
            apiInstance.listStakings(poolId, statuses, walletId, tokenId, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#listStakings");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	poolId := "babylon_btc"
  	statuses := "Active,StakeInProgress,"
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	tokenId := "ETH_USDT"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.ListStakings(ctx).
  		PoolId(poolId).
  		Statuses(statuses).
  		WalletId(walletId).
  		TokenId(tokenId).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `StakingsAPI.ListStakings``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListStakings`: ListStakings200Response
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.ListStakings`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    pool_id: "babylon_btc",
    statuses: "Active,StakeInProgress,",
    wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
    token_id: "ETH_USDT",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listStakings(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List staking positions eligible for Babylon Phase-2
Source: https://cobo.com/developers/v2/api-references/stakings/list-staking-positions-eligible-for-babylon-phase-2

get /stakings/protocols/babylon/stakings/eligibles
This operation lists all staking positions that are eligible for Babylon Phase-2. If an eligible staking position's status is `Unregistered`, you can initiate a registration for it. You can filter the results by registration status.

You can use this operation to:
- Check which staking positions can be registered
- Get staking details before initiating registration
- Monitor available positions for registration

As registration is an asynchronous process and might take some time to complete, it is recommended that you regularly call this operation to check staking position eligibility and register eligible positions on time.

For more information, refer to [Babylon's official doc](https://github.com/babylonlabs-io/babylon/tree/main/docs).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_babylon_eligible_stakings200_response import (
      ListBabylonEligibleStakings200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      status = "Registered"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List staking positions eligible for Babylon Phase-2
          api_response = api_instance.list_babylon_eligible_stakings(
              status=status, limit=limit, before=before, after=after
          )
          print("The response of StakingsApi->list_babylon_eligible_stakings:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling StakingsApi->list_babylon_eligible_stakings: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String status = "Registered";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListBabylonEligibleStakings200Response result =
            apiInstance.listBabylonEligibleStakings(status, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#listBabylonEligibleStakings");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	status := "Registered"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.ListBabylonEligibleStakings(ctx).
  		Status(status).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.ListBabylonEligibleStakings``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListBabylonEligibleStakings`: ListBabylonEligibleStakings200Response
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.ListBabylonEligibleStakings`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    status: "Registered",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listBabylonEligibleStakings(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List wallets eligible for Babylon airdrop
Source: https://cobo.com/developers/v2/api-references/stakings/list-wallets-eligible-for-babylon-airdrop

get /stakings/protocols/babylon/airdrops/eligibles
This operation lists all wallets that are eligible for the Babylon airdrop. If an eligible wallet's status is `Unregistered`, you can initiate an airdrop registration for it. You can filter the results by airdrop registration status.

You can use this operation to:
- Check which wallets are eligible for airdrop registrations
- Estimate airdrop amounts before claiming
- Monitor available airdrop

As registration is an asynchronous process and might take some time to complete, it is recommended that you regularly call this operation to check wallet eligibility and register eligible wallets on time.

For more information, refer to [Babylon's official doc](https://github.com/babylonlabs-io/babylon/tree/main/docs).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_babylon_eligible_airdrops200_response import (
      ListBabylonEligibleAirdrops200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      status = "Registered"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List wallets eligible for Babylon airdrop
          api_response = api_instance.list_babylon_eligible_airdrops(
              status=status, limit=limit, before=before, after=after
          )
          print("The response of StakingsApi->list_babylon_eligible_airdrops:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling StakingsApi->list_babylon_eligible_airdrops: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      String status = "Registered";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListBabylonEligibleAirdrops200Response result =
            apiInstance.listBabylonEligibleAirdrops(status, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#listBabylonEligibleAirdrops");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	status := "Registered"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.ListBabylonEligibleAirdrops(ctx).
  		Status(status).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.ListBabylonEligibleAirdrops``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListBabylonEligibleAirdrops`: ListBabylonEligibleAirdrops200Response
  	fmt.Fprintf(os.Stdout, "Response from `StakingsAPI.ListBabylonEligibleAirdrops`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    status: "Registered",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listBabylonEligibleAirdrops(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Register for Babylon airdrop
Source: https://cobo.com/developers/v2/api-references/stakings/register-for-babylon-airdrop

post /stakings/protocols/babylon/airdrops/registrations
This operation initiates a Babylon airdrop registration request. 

Before calling this operation, please ensure the following:
- The Bitcoin (BTC) address is eligible for the Babylon airdrop and has not been registered. You can call the [List wallets eligible for Babylon airdrop](https://www.cobo.com/developers/v2/api-references/stakings/list-wallets-eligible-for-babylon-airdrop) operation to check the registration status.
- The Babylon address has enough asset to pay for the registration fee.
- The Babylon address must be a Babylon address in an MPC Wallet in your organization.

The system first checks whether the provided address is eligible for the Babylon airdrop. If eligible, it creates a unique registration ID, which can be used to track the status. 

The registration is processed asynchronously and may take some time to complete. It is recommended that you regularly call the [Get Babylon airdrop registration details](https://www.cobo.com/developers/v2/api-references/stakings/get-babylon-airdrop-registration-details) operation to check the status and handle registration accordingly.

For more information, refer to [Babylon's official doc](https://github.com/babylonlabs-io/babylon/tree/main/docs).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_babylon_airdrop_registration201_response import (
      CreateBabylonAirdropRegistration201Response,
  )
  from cobo_waas2.models.create_babylon_airdrop_registration_request import (
      CreateBabylonAirdropRegistrationRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      create_babylon_airdrop_registration_request = (
          cobo_waas2.CreateBabylonAirdropRegistrationRequest()
      )

      try:
          # Register for Babylon airdrop
          api_response = api_instance.create_babylon_airdrop_registration(
              create_babylon_airdrop_registration_request=create_babylon_airdrop_registration_request
          )
          print("The response of StakingsApi->create_babylon_airdrop_registration:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling StakingsApi->create_babylon_airdrop_registration: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      CreateBabylonAirdropRegistrationRequest createBabylonAirdropRegistrationRequest =
          new CreateBabylonAirdropRegistrationRequest();
      try {
        CreateBabylonAirdropRegistration201Response result =
            apiInstance.createBabylonAirdropRegistration(createBabylonAirdropRegistrationRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#createBabylonAirdropRegistration");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createBabylonAirdropRegistrationRequest := *coboWaas2.NewCreateBabylonAirdropRegistrationRequest()

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.CreateBabylonAirdropRegistration(ctx).
  		CreateBabylonAirdropRegistrationRequest(createBabylonAirdropRegistrationRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.CreateBabylonAirdropRegistration``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateBabylonAirdropRegistration`: CreateBabylonAirdropRegistration201Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `StakingsAPI.CreateBabylonAirdropRegistration`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    CreateBabylonAirdropRegistrationRequest:
      new CoboWaas2.CreateBabylonAirdropRegistrationRequest(),
  };
  apiInstance.createBabylonAirdropRegistration(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Register for Babylon Phase-2
Source: https://cobo.com/developers/v2/api-references/stakings/register-for-babylon-phase-2

post /stakings/protocols/babylon/stakings/registrations
This operation initiates a Babylon Phase-2 registration request. 

Before calling this operation, please ensure the following:
- The staking position is eligible for the Babylon Phase-2 and has not been registered. You can call the [List staking positions eligible for Babylon Phase-2](https://www.cobo.com/developers/v2/api-references/stakings/list-staking-positions-eligible-for-babylon-phase-2) operation to check the registration status.
- The Babylon address has enough asset to pay for the registration fee.
- The Babylon address must be a Babylon address in an MPC Wallet in your organization.

The system first checks whether the provided address is eligible for Phase-2. If eligible, it creates a unique registration ID, which can be used to track the status. 

The registration is processed asynchronously and may take some time to complete. It is recommended that you regularly call the [Get Babylon Phase-2 registration details](https://www.cobo.com/developers/v2/api-references/stakings/get-babylon-phase-2-registration-details) operation to check the status and handle registration accordingly.

For more information, refer to [Babylon's official doc](https://github.com/babylonlabs-io/babylon/tree/main/docs).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_babylon_staking_registration201_response import (
      CreateBabylonStakingRegistration201Response,
  )
  from cobo_waas2.models.create_babylon_staking_registration_request import (
      CreateBabylonStakingRegistrationRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.StakingsApi(api_client)
      create_babylon_staking_registration_request = (
          cobo_waas2.CreateBabylonStakingRegistrationRequest()
      )

      try:
          # Register for Babylon Phase-2
          api_response = api_instance.create_babylon_staking_registration(
              create_babylon_staking_registration_request=create_babylon_staking_registration_request
          )
          print("The response of StakingsApi->create_babylon_staking_registration:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling StakingsApi->create_babylon_staking_registration: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.StakingsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      StakingsApi apiInstance = new StakingsApi();
      CreateBabylonStakingRegistrationRequest createBabylonStakingRegistrationRequest =
          new CreateBabylonStakingRegistrationRequest();
      try {
        CreateBabylonStakingRegistration201Response result =
            apiInstance.createBabylonStakingRegistration(createBabylonStakingRegistrationRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling StakingsApi#createBabylonStakingRegistration");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createBabylonStakingRegistrationRequest := *coboWaas2.NewCreateBabylonStakingRegistrationRequest()

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.StakingsAPI.CreateBabylonStakingRegistration(ctx).
  		CreateBabylonStakingRegistrationRequest(createBabylonStakingRegistrationRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `StakingsAPI.CreateBabylonStakingRegistration``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateBabylonStakingRegistration`: CreateBabylonStakingRegistration201Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `StakingsAPI.CreateBabylonStakingRegistration`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.StakingsApi();
  const opts = {
    CreateBabylonStakingRegistrationRequest:
      new CoboWaas2.CreateBabylonStakingRegistrationRequest(),
  };
  apiInstance.createBabylonStakingRegistration(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Activate or deactivate allowlist
Source: https://cobo.com/developers/v2/api-references/tokenization/activate-or-deactivate-allowlist

post /tokenization/tokens/{token_id}/allowlist/activation
This operation activates or deactivates the allowlist.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_allowlist_activation_request import (
      TokenizationAllowlistActivationRequest,
  )
  from cobo_waas2.models.tokenization_operation_response import (
      TokenizationOperationResponse,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      tokenization_allowlist_activation_request = (
          cobo_waas2.TokenizationAllowlistActivationRequest(
              source=cobo_waas2.TokenizationTokenOperationSource(
                  cobo_waas2.TokenizationMpcOperationSource(
                      source_type="Org-Controlled",
                      wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                      address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
                  )
              ),
              activation=True,
              fee=cobo_waas2.TransactionRequestFee(
                  cobo_waas2.TransactionRequestFixedFee(
                      fee_type="EVM_EIP_1559", token_id="TRON"
                  )
              ),
          )
      )

      try:
          # Activate or deactivate allowlist
          api_response = api_instance.update_tokenization_allowlist_activation(
              token_id,
              tokenization_allowlist_activation_request=tokenization_allowlist_activation_request,
          )
          print(
              "The response of TokenizationApi->update_tokenization_allowlist_activation:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->update_tokenization_allowlist_activation: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      TokenizationAllowlistActivationRequest tokenizationAllowlistActivationRequest =
          new TokenizationAllowlistActivationRequest()
              .source(
                  new TokenizationTokenOperationSource(
                      new TokenizationMpcOperationSource()
                          .sourceType(TokenizationOperationSourceType.ORG_CONTROLLED)
                          .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                          .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")))
              .activation(true)
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        TokenizationOperationResponse result =
            apiInstance.updateTokenizationAllowlistActivation(
                tokenId, tokenizationAllowlistActivationRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling TokenizationApi#updateTokenizationAllowlistActivation");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	tokenizationAllowlistActivationRequest := *coboWaas2.NewTokenizationAllowlistActivationRequest(coboWaas2.TokenizationTokenOperationSource{TokenizationMpcOperationSource: coboWaas2.NewTokenizationMpcOperationSource(coboWaas2.TokenizationOperationSourceType("Org-Controlled"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")}, true, coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.UpdateTokenizationAllowlistActivation(ctx, tokenId).
  		TokenizationAllowlistActivationRequest(tokenizationAllowlistActivationRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.UpdateTokenizationAllowlistActivation``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UpdateTokenizationAllowlistActivation`: TokenizationOperationResponse
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TokenizationAPI.UpdateTokenizationAllowlistActivation`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const opts = {
    TokenizationAllowlistActivationRequest:
      CoboWaas2.TokenizationAllowlistActivationRequest.constructFromObject({
        source: {
          source_type: "Org-Controlled",
          wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
          address: "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
        },
        activation: true,
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
      }),
  };
  apiInstance.updateTokenizationAllowlistActivation(token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Burn tokens
Source: https://cobo.com/developers/v2/api-references/tokenization/burn-tokens

post /tokenization/tokens/{token_id}/burn
This operation burns tokens from a specified address.
Creates a burn transaction that will decrease the token supply.

**Note**: This operation is not supported for CoboERC20Wrapper and SOLWrapper tokens.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_burn_token_request import (
      TokenizationBurnTokenRequest,
  )
  from cobo_waas2.models.tokenization_operation_response import (
      TokenizationOperationResponse,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      tokenization_burn_token_request = cobo_waas2.TokenizationBurnTokenRequest(
          source=cobo_waas2.TokenizationTokenOperationSource(
              cobo_waas2.TokenizationMpcOperationSource(
                  source_type="Org-Controlled",
                  wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                  address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
              )
          ),
          burns=[
              cobo_waas2.TokenizationBurnTokenParamsBurnsInner(
                  amount="0.99", from_address="0x051A924H4dCb264226d7B036C2893a0D344"
              )
          ],
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          ),
      )

      try:
          # Burn tokens
          api_response = api_instance.burn_tokenization(
              token_id, tokenization_burn_token_request=tokenization_burn_token_request
          )
          print("The response of TokenizationApi->burn_tokenization:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TokenizationApi->burn_tokenization: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      TokenizationBurnTokenRequest tokenizationBurnTokenRequest =
          new TokenizationBurnTokenRequest()
              .source(
                  new TokenizationTokenOperationSource(
                      new TokenizationMpcOperationSource()
                          .sourceType(TokenizationOperationSourceType.ORG_CONTROLLED)
                          .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                          .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")))
              .burns(
                  Arrays.asList(
                      new TokenizationBurnTokenParamsBurnsInner()
                          .amount("0.99")
                          .fromAddress("0x051A924H4dCb264226d7B036C2893a0D344")))
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        TokenizationOperationResponse result =
            apiInstance.burnTokenization(tokenId, tokenizationBurnTokenRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#burnTokenization");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	tokenizationBurnTokenRequest := *coboWaas2.NewTokenizationBurnTokenRequest(coboWaas2.TokenizationTokenOperationSource{TokenizationMpcOperationSource: coboWaas2.NewTokenizationMpcOperationSource(coboWaas2.TokenizationOperationSourceType("Org-Controlled"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")}, []coboWaas2.TokenizationBurnTokenParamsBurnsInner{*coboWaas2.NewTokenizationBurnTokenParamsBurnsInner("0.99", "0x051A924H4dCb264226d7B036C2893a0D344")}, coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.BurnTokenization(ctx, tokenId).
  		TokenizationBurnTokenRequest(tokenizationBurnTokenRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `TokenizationAPI.BurnTokenization``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `BurnTokenization`: TokenizationOperationResponse
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.BurnTokenization`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const opts = {
    TokenizationBurnTokenRequest:
      CoboWaas2.TokenizationBurnTokenRequest.constructFromObject({
        source: {
          source_type: "Org-Controlled",
          wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
          address: "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
        },
        burns: [
          {
            amount: "0.99",
            from_address: "0x051A924H4dCb264226d7B036C2893a0D344",
          },
        ],
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
      }),
  };
  apiInstance.burnTokenization(token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Call token contract
Source: https://cobo.com/developers/v2/api-references/tokenization/call-token-contract

post /tokenization/tokens/{token_id}/contract_call
This operation performs a contract call on the token contract.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_contract_call_request import (
      TokenizationContractCallRequest,
  )
  from cobo_waas2.models.tokenization_operation_response import (
      TokenizationOperationResponse,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      tokenization_contract_call_request = cobo_waas2.TokenizationContractCallRequest(
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          )
      )

      try:
          # Call token contract
          api_response = api_instance.tokenization_contract_call(
              token_id,
              tokenization_contract_call_request=tokenization_contract_call_request,
          )
          print("The response of TokenizationApi->tokenization_contract_call:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->tokenization_contract_call: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      TokenizationContractCallRequest tokenizationContractCallRequest =
          new TokenizationContractCallRequest()
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        TokenizationOperationResponse result =
            apiInstance.tokenizationContractCall(tokenId, tokenizationContractCallRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#tokenizationContractCall");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	tokenizationContractCallRequest := *coboWaas2.NewTokenizationContractCallRequest(coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.TokenizationContractCall(ctx, tokenId).
  		TokenizationContractCallRequest(tokenizationContractCallRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.TokenizationContractCall``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `TokenizationContractCall`: TokenizationOperationResponse
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.TokenizationContractCall`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const opts = {
    TokenizationContractCallRequest:
      CoboWaas2.TokenizationContractCallRequest.constructFromObject({
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
      }),
  };
  apiInstance.tokenizationContractCall(token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Estimate tokenization operation fee
Source: https://cobo.com/developers/v2/api-references/tokenization/estimate-tokenization-operation-fee

post /tokenization/estimate_fee
This operation estimates the fee required for tokenization operations.
For EVM-based chains, this calculates the gas cost for the specified operation.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.estimated_fee import EstimatedFee
  from cobo_waas2.models.tokenization_estimate_fee_request import (
      TokenizationEstimateFeeRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      tokenization_estimate_fee_request = cobo_waas2.TokenizationEstimateFeeRequest(
          operation_params=cobo_waas2.TokenizationEstimateFeeRequestOperationParams(
              cobo_waas2.TokenizationIssueEstimateFeeParams(
                  chain_id="ETH",
                  source=cobo_waas2.TokenizationTokenOperationSource(
                      cobo_waas2.TokenizationMpcOperationSource(
                          source_type="Org-Controlled",
                          wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                          address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
                      )
                  ),
                  token_params=cobo_waas2.TokenizationIssueTokenParamsTokenParams(
                      cobo_waas2.TokenizationERC20TokenParams(
                          standard="ERC20",
                          name="My Awesome Token",
                          symbol="MAT",
                          decimals=18,
                      )
                  ),
                  operation_type="Issue",
              )
          )
      )

      try:
          # Estimate tokenization operation fee
          api_response = api_instance.estimate_tokenization_fee(
              tokenization_estimate_fee_request
          )
          print("The response of TokenizationApi->estimate_tokenization_fee:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->estimate_tokenization_fee: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      TokenizationEstimateFeeRequest tokenizationEstimateFeeRequest =
          new TokenizationEstimateFeeRequest()
              .operationParams(
                  new TokenizationEstimateFeeRequestOperationParams(
                      new TokenizationIssueEstimateFeeParams()
                          .chainId("ETH")
                          .source(
                              new TokenizationTokenOperationSource(
                                  new TokenizationMpcOperationSource()
                                      .sourceType(TokenizationOperationSourceType.ORG_CONTROLLED)
                                      .walletId(
                                          UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                                      .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")))
                          .tokenParams(
                              new TokenizationIssueTokenParamsTokenParams(
                                  new TokenizationERC20TokenParams()
                                      .standard(TokenizationTokenStandard.ERC20)
                                      .name("My Awesome Token")
                                      .symbol("MAT")
                                      .decimals(18)))
                          .operationType(TokenizationOperationType.ISSUE)));
      try {
        EstimatedFee result = apiInstance.estimateTokenizationFee(tokenizationEstimateFeeRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#estimateTokenizationFee");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenizationEstimateFeeRequest := *coboWaas2.NewTokenizationEstimateFeeRequest(coboWaas2.TokenizationEstimateFeeRequest_operation_params{TokenizationBurnEstimateFeeParams: coboWaas2.NewTokenizationBurnEstimateFeeParams(coboWaas2.TokenizationTokenOperationSource{TokenizationMpcOperationSource: coboWaas2.NewTokenizationMpcOperationSource(coboWaas2.TokenizationOperationSourceType("Org-Controlled"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")}, []coboWaas2.TokenizationBurnTokenParamsBurnsInner{*coboWaas2.NewTokenizationBurnTokenParamsBurnsInner("0.99", "0x051A924H4dCb264226d7B036C2893a0D344")}, coboWaas2.TokenizationOperationType("Issue"), "8a4f9324-ef2a-43cf-9f0e-d7f99999d3e8")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.EstimateTokenizationFee(ctx).
  		TokenizationEstimateFeeRequest(tokenizationEstimateFeeRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.EstimateTokenizationFee``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `EstimateTokenizationFee`: EstimatedFee
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.EstimateTokenizationFee`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const TokenizationEstimateFeeRequest =
    new CoboWaas2.TokenizationEstimateFeeRequest();
  apiInstance.estimateTokenizationFee(TokenizationEstimateFeeRequest).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get allowlist activation status
Source: https://cobo.com/developers/v2/api-references/tokenization/get-allowlist-activation-status

get /tokenization/tokens/{token_id}/allowlist/activation
This operation retrieves the allowlist activation status of the token contract.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.get_tokenization_allowlist_activation200_response import (
      GetTokenizationAllowlistActivation200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"

      try:
          # Get allowlist activation status
          api_response = api_instance.get_tokenization_allowlist_activation(token_id)
          print(
              "The response of TokenizationApi->get_tokenization_allowlist_activation:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->get_tokenization_allowlist_activation: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      try {
        GetTokenizationAllowlistActivation200Response result =
            apiInstance.getTokenizationAllowlistActivation(tokenId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling TokenizationApi#getTokenizationAllowlistActivation");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.GetTokenizationAllowlistActivation(ctx, tokenId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.GetTokenizationAllowlistActivation``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetTokenizationAllowlistActivation`: GetTokenizationAllowlistActivation200Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TokenizationAPI.GetTokenizationAllowlistActivation`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  apiInstance.getTokenizationAllowlistActivation(token_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get token details
Source: https://cobo.com/developers/v2/api-references/tokenization/get-token-details

get /tokenization/tokens/{token_id}
This operation retrieves the detailed information for a specific issued token by its ID.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_token_detail_info import TokenizationTokenDetailInfo
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"

      try:
          # Get token details
          api_response = api_instance.get_tokenization_info(token_id)
          print("The response of TokenizationApi->get_tokenization_info:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TokenizationApi->get_tokenization_info: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      try {
        TokenizationTokenDetailInfo result = apiInstance.getTokenizationInfo(tokenId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#getTokenizationInfo");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.GetTokenizationInfo(ctx, tokenId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.GetTokenizationInfo``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetTokenizationInfo`: TokenizationTokenDetailInfo
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.GetTokenizationInfo`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  apiInstance.getTokenizationInfo(token_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get token holdings information
Source: https://cobo.com/developers/v2/api-references/tokenization/get-token-holdings-information

get /tokenization/tokens/{token_id}/holdings
This operation retrieves the holdings information for a specific issued token,
showing which wallets hold the token and their respective balances.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_list_holdings_response import (
      TokenizationListHoldingsResponse,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # Get token holdings information
          api_response = api_instance.list_tokenization_holdings(
              token_id, limit=limit, before=before, after=after
          )
          print("The response of TokenizationApi->list_tokenization_holdings:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->list_tokenization_holdings: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        TokenizationListHoldingsResponse result =
            apiInstance.listTokenizationHoldings(tokenId, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#listTokenizationHoldings");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.ListTokenizationHoldings(ctx, tokenId).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.ListTokenizationHoldings``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTokenizationHoldings`: TokenizationListHoldingsResponse
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.ListTokenizationHoldings`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const opts = {
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listTokenizationHoldings(token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get tokenization activity details
Source: https://cobo.com/developers/v2/api-references/tokenization/get-tokenization-activity-details

get /tokenization/activities/{activity_id}
This operation retrieves the detailed information for a specific tokenization activity by its ID.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_activity_info import TokenizationActivityInfo
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      activity_id = "b7c8e9d0-f1a2-3b4c-5d6e-7f8a9b0c1d2e"

      try:
          # Get tokenization activity details
          api_response = api_instance.get_tokenization_activity(activity_id)
          print("The response of TokenizationApi->get_tokenization_activity:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->get_tokenization_activity: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      UUID activityId = UUID.fromString("b7c8e9d0-f1a2-3b4c-5d6e-7f8a9b0c1d2e");
      try {
        TokenizationActivityInfo result = apiInstance.getTokenizationActivity(activityId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#getTokenizationActivity");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	activityId := "b7c8e9d0-f1a2-3b4c-5d6e-7f8a9b0c1d2e"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.GetTokenizationActivity(ctx, activityId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.GetTokenizationActivity``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetTokenizationActivity`: TokenizationActivityInfo
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.GetTokenizationActivity`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const activity_id = "b7c8e9d0-f1a2-3b4c-5d6e-7f8a9b0c1d2e";
  apiInstance.getTokenizationActivity(activity_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Issue token
Source: https://cobo.com/developers/v2/api-references/tokenization/issue-token

post /tokenization/tokens
This operation issues a new token contract. It supports various blockchain platforms.

For EVM-based chains, this involves issuing a new smart contract from a template.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_issued_token_request import (
      TokenizationIssuedTokenRequest,
  )
  from cobo_waas2.models.tokenization_operation_response import (
      TokenizationOperationResponse,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      tokenization_issued_token_request = cobo_waas2.TokenizationIssuedTokenRequest(
          chain_id="ETH",
          source=cobo_waas2.TokenizationTokenOperationSource(
              cobo_waas2.TokenizationMpcOperationSource(
                  source_type="Org-Controlled",
                  wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                  address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
              )
          ),
          token_params=cobo_waas2.TokenizationIssueTokenParamsTokenParams(
              cobo_waas2.TokenizationERC20TokenParams(
                  standard="ERC20", name="My Awesome Token", symbol="MAT", decimals=18
              )
          ),
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          ),
      )

      try:
          # Issue token
          api_response = api_instance.issue_token(tokenization_issued_token_request)
          print("The response of TokenizationApi->issue_token:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TokenizationApi->issue_token: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      TokenizationIssuedTokenRequest tokenizationIssuedTokenRequest =
          new TokenizationIssuedTokenRequest()
              .chainId("ETH")
              .source(
                  new TokenizationTokenOperationSource(
                      new TokenizationMpcOperationSource()
                          .sourceType(TokenizationOperationSourceType.ORG_CONTROLLED)
                          .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                          .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")))
              .tokenParams(
                  new TokenizationIssueTokenParamsTokenParams(
                      new TokenizationERC20TokenParams()
                          .standard(TokenizationTokenStandard.ERC20)
                          .name("My Awesome Token")
                          .symbol("MAT")
                          .decimals(18)))
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        TokenizationOperationResponse result = apiInstance.issueToken(tokenizationIssuedTokenRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#issueToken");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenizationIssuedTokenRequest := *coboWaas2.NewTokenizationIssuedTokenRequest("ETH", coboWaas2.TokenizationTokenOperationSource{TokenizationMpcOperationSource: coboWaas2.NewTokenizationMpcOperationSource(coboWaas2.TokenizationOperationSourceType("Org-Controlled"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")}, coboWaas2.TokenizationIssueTokenParams_token_params{TokenizationERC20TokenParams: coboWaas2.NewTokenizationERC20TokenParams(coboWaas2.TokenizationTokenStandard("ERC20"), "My Awesome Token", "MAT", int32(18))}, coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.IssueToken(ctx).
  		TokenizationIssuedTokenRequest(tokenizationIssuedTokenRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `TokenizationAPI.IssueToken``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `IssueToken`: TokenizationOperationResponse
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.IssueToken`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const TokenizationIssuedTokenRequest =
    new CoboWaas2.TokenizationIssuedTokenRequest();
  apiInstance.issueToken(TokenizationIssuedTokenRequest).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List addresses on allowlist
Source: https://cobo.com/developers/v2/api-references/tokenization/list-addresses-on-allowlist

get /tokenization/tokens/{token_id}/allowlist/addresses
This operation lists addresses on the allowlist.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_allowlist_addresses_response import (
      TokenizationAllowlistAddressesResponse,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      limit = 10
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      direction = "ASC"

      try:
          # List addresses on allowlist
          api_response = api_instance.list_tokenization_allowlist_addresses(
              token_id, limit=limit, after=after, before=before, direction=direction
          )
          print(
              "The response of TokenizationApi->list_tokenization_allowlist_addresses:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->list_tokenization_allowlist_addresses: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      Integer limit = 10;
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String direction = "ASC";
      try {
        TokenizationAllowlistAddressesResponse result =
            apiInstance.listTokenizationAllowlistAddresses(tokenId, limit, after, before, direction);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling TokenizationApi#listTokenizationAllowlistAddresses");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	limit := int32(10)
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	direction := "ASC"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.ListTokenizationAllowlistAddresses(ctx, tokenId).
  		Limit(limit).
  		After(after).
  		Before(before).
  		Direction(direction).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.ListTokenizationAllowlistAddresses``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTokenizationAllowlistAddresses`: TokenizationAllowlistAddressesResponse
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TokenizationAPI.ListTokenizationAllowlistAddresses`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const opts = {
    limit: 10,
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    direction: "ASC",
  };
  apiInstance.listTokenizationAllowlistAddresses(token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List addresses on blocklist
Source: https://cobo.com/developers/v2/api-references/tokenization/list-addresses-on-blocklist

get /tokenization/tokens/{token_id}/blocklist/addresses
This operation lists addresses on the blocklist.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_tokenization_blocklist_addresses200_response import (
      ListTokenizationBlocklistAddresses200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      limit = 10
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      direction = "ASC"

      try:
          # List addresses on blocklist
          api_response = api_instance.list_tokenization_blocklist_addresses(
              token_id, limit=limit, after=after, before=before, direction=direction
          )
          print(
              "The response of TokenizationApi->list_tokenization_blocklist_addresses:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->list_tokenization_blocklist_addresses: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      Integer limit = 10;
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String direction = "ASC";
      try {
        ListTokenizationBlocklistAddresses200Response result =
            apiInstance.listTokenizationBlocklistAddresses(tokenId, limit, after, before, direction);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling TokenizationApi#listTokenizationBlocklistAddresses");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	limit := int32(10)
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	direction := "ASC"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.ListTokenizationBlocklistAddresses(ctx, tokenId).
  		Limit(limit).
  		After(after).
  		Before(before).
  		Direction(direction).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.ListTokenizationBlocklistAddresses``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTokenizationBlocklistAddresses`: ListTokenizationBlocklistAddresses200Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TokenizationAPI.ListTokenizationBlocklistAddresses`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const opts = {
    limit: 10,
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    direction: "ASC",
  };
  apiInstance.listTokenizationBlocklistAddresses(token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List issued tokens
Source: https://cobo.com/developers/v2/api-references/tokenization/list-issued-tokens

get /tokenization/tokens
This operation retrieves a list of tokens issued by the organization.
Returns issued token information including total supply, holdings, and token status.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_list_token_info_response import (
      TokenizationListTokenInfoResponse,
  )
  from cobo_waas2.models.tokenization_status import TokenizationStatus
  from cobo_waas2.models.tokenization_token_standard import TokenizationTokenStandard
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      chain_id = "ETH"
      token_id = "ETH_USDT"
      token_standard = "ERC20"
      status = "Processing"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List issued tokens
          api_response = api_instance.list_issued_tokens(
              chain_id=chain_id,
              token_id=token_id,
              token_standard=token_standard,
              status=status,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of TokenizationApi->list_issued_tokens:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TokenizationApi->list_issued_tokens: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String chainId = "ETH";
      String tokenId = "ETH_USDT";
      TokenizationTokenStandard tokenStandard = TokenizationTokenStandard.fromValue("ERC20");
      TokenizationStatus status = TokenizationStatus.fromValue("Processing");
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        TokenizationListTokenInfoResponse result =
            apiInstance.listIssuedTokens(
                chainId, tokenId, tokenStandard, status, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#listIssuedTokens");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	chainId := "ETH"
  	tokenId := "ETH_USDT"
  	tokenStandard := coboWaas2.TokenizationTokenStandard("ERC20")
  	status := coboWaas2.TokenizationStatus("Processing")
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.ListIssuedTokens(ctx).
  		ChainId(chainId).
  		TokenId(tokenId).
  		TokenStandard(tokenStandard).
  		Status(status).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `TokenizationAPI.ListIssuedTokens``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListIssuedTokens`: TokenizationListTokenInfoResponse
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.ListIssuedTokens`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const opts = {
    chain_id: "ETH",
    token_id: "ETH_USDT",
    token_standard: "ERC20",
    status: "Processing",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listIssuedTokens(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List supported chains for tokenization
Source: https://cobo.com/developers/v2/api-references/tokenization/list-supported-chains-for-tokenization

get /tokenization/enabled_chains
This operation retrieves a list of tokenization supported chains.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_list_enabled_chains_response import (
      TokenizationListEnabledChainsResponse,
  )
  from cobo_waas2.models.tokenization_token_standard import TokenizationTokenStandard
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_standard = "ERC20"
      limit = 10
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"

      try:
          # List supported chains for tokenization
          api_response = api_instance.list_tokenization_supported_chains(
              token_standard=token_standard, limit=limit, after=after, before=before
          )
          print("The response of TokenizationApi->list_tokenization_supported_chains:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->list_tokenization_supported_chains: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      TokenizationTokenStandard tokenStandard = TokenizationTokenStandard.fromValue("ERC20");
      Integer limit = 10;
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      try {
        TokenizationListEnabledChainsResponse result =
            apiInstance.listTokenizationSupportedChains(tokenStandard, limit, after, before);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#listTokenizationSupportedChains");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenStandard := coboWaas2.TokenizationTokenStandard("ERC20")
  	limit := int32(10)
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.ListTokenizationSupportedChains(ctx).
  		TokenStandard(tokenStandard).
  		Limit(limit).
  		After(after).
  		Before(before).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.ListTokenizationSupportedChains``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTokenizationSupportedChains`: TokenizationListEnabledChainsResponse
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TokenizationAPI.ListTokenizationSupportedChains`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const opts = {
    token_standard: "ERC20",
    limit: 10,
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
  };
  apiInstance.listTokenizationSupportedChains(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List token permissions
Source: https://cobo.com/developers/v2/api-references/tokenization/list-token-permissions

get /tokenization/tokens/{token_id}/permissions
This operation retrieves the permission settings for a tokenization contract.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_list_permissions_response import (
      TokenizationListPermissionsResponse,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
      limit = 10
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      direction = "ASC"

      try:
          # List token permissions
          api_response = api_instance.list_tokenization_permissions(
              token_id,
              address=address,
              limit=limit,
              after=after,
              before=before,
              direction=direction,
          )
          print("The response of TokenizationApi->list_tokenization_permissions:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->list_tokenization_permissions: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      String address = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045";
      Integer limit = 10;
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String direction = "ASC";
      try {
        TokenizationListPermissionsResponse result =
            apiInstance.listTokenizationPermissions(
                tokenId, address, limit, after, before, direction);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#listTokenizationPermissions");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	address := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045"
  	limit := int32(10)
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	direction := "ASC"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.ListTokenizationPermissions(ctx, tokenId).
  		Address(address).
  		Limit(limit).
  		After(after).
  		Before(before).
  		Direction(direction).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.ListTokenizationPermissions``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTokenizationPermissions`: TokenizationListPermissionsResponse
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TokenizationAPI.ListTokenizationPermissions`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const opts = {
    address: "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
    limit: 10,
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    direction: "ASC",
  };
  apiInstance.listTokenizationPermissions(token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List tokenization activities
Source: https://cobo.com/developers/v2/api-references/tokenization/list-tokenization-activities

get /tokenization/activities
This operation retrieves a list of tokenization activities.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_activity_status import TokenizationActivityStatus
  from cobo_waas2.models.tokenization_list_activities_response import (
      TokenizationListActivitiesResponse,
  )
  from cobo_waas2.models.tokenization_operation_type import TokenizationOperationType
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      activity_type = "Issue"
      activity_status = "Processing"
      limit = 10
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      direction = "ASC"

      try:
          # List tokenization activities
          api_response = api_instance.list_tokenization_activities(
              token_id=token_id,
              activity_type=activity_type,
              activity_status=activity_status,
              limit=limit,
              after=after,
              before=before,
              direction=direction,
          )
          print("The response of TokenizationApi->list_tokenization_activities:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->list_tokenization_activities: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      TokenizationOperationType activityType = TokenizationOperationType.fromValue("Issue");
      TokenizationActivityStatus activityStatus = TokenizationActivityStatus.fromValue("Processing");
      Integer limit = 10;
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String direction = "ASC";
      try {
        TokenizationListActivitiesResponse result =
            apiInstance.listTokenizationActivities(
                tokenId, activityType, activityStatus, limit, after, before, direction);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#listTokenizationActivities");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	activityType := coboWaas2.TokenizationOperationType("Issue")
  	activityStatus := coboWaas2.TokenizationActivityStatus("Processing")
  	limit := int32(10)
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	direction := "ASC"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.ListTokenizationActivities(ctx).
  		TokenId(tokenId).
  		ActivityType(activityType).
  		ActivityStatus(activityStatus).
  		Limit(limit).
  		After(after).
  		Before(before).
  		Direction(direction).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.ListTokenizationActivities``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTokenizationActivities`: TokenizationListActivitiesResponse
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.ListTokenizationActivities`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const opts = {
    token_id: "ETH_USDT",
    activity_type: "Issue",
    activity_status: "Processing",
    limit: 10,
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    direction: "ASC",
  };
  apiInstance.listTokenizationActivities(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Mint tokens
Source: https://cobo.com/developers/v2/api-references/tokenization/mint-tokens

post /tokenization/tokens/{token_id}/mint
This operation mints new tokens to a specified address.
Creates a mint transaction that will increase the token supply.

**Note**: This operation is not supported for CoboERC20Wrapper and SOLWrapper tokens.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_mint_token_request import (
      TokenizationMintTokenRequest,
  )
  from cobo_waas2.models.tokenization_operation_response import (
      TokenizationOperationResponse,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      tokenization_mint_token_request = cobo_waas2.TokenizationMintTokenRequest(
          source=cobo_waas2.TokenizationTokenOperationSource(
              cobo_waas2.TokenizationMpcOperationSource(
                  source_type="Org-Controlled",
                  wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                  address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
              )
          ),
          mints=[
              cobo_waas2.TokenizationMintTokenParamsMintsInner(
                  amount="0.99", to_address="0x051A924H4dCb264226d7B036C2893a0D344"
              )
          ],
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          ),
      )

      try:
          # Mint tokens
          api_response = api_instance.mint_tokenization(
              token_id, tokenization_mint_token_request
          )
          print("The response of TokenizationApi->mint_tokenization:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TokenizationApi->mint_tokenization: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      TokenizationMintTokenRequest tokenizationMintTokenRequest =
          new TokenizationMintTokenRequest()
              .source(
                  new TokenizationTokenOperationSource(
                      new TokenizationMpcOperationSource()
                          .sourceType(TokenizationOperationSourceType.ORG_CONTROLLED)
                          .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                          .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")))
              .mints(
                  Arrays.asList(
                      new TokenizationMintTokenParamsMintsInner()
                          .amount("0.99")
                          .toAddress("0x051A924H4dCb264226d7B036C2893a0D344")))
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        TokenizationOperationResponse result =
            apiInstance.mintTokenization(tokenId, tokenizationMintTokenRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#mintTokenization");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	tokenizationMintTokenRequest := *coboWaas2.NewTokenizationMintTokenRequest(coboWaas2.TokenizationTokenOperationSource{TokenizationMpcOperationSource: coboWaas2.NewTokenizationMpcOperationSource(coboWaas2.TokenizationOperationSourceType("Org-Controlled"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")}, []coboWaas2.TokenizationMintTokenParamsMintsInner{*coboWaas2.NewTokenizationMintTokenParamsMintsInner("0.99", "0x051A924H4dCb264226d7B036C2893a0D344")}, coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.MintTokenization(ctx, tokenId).
  		TokenizationMintTokenRequest(tokenizationMintTokenRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `TokenizationAPI.MintTokenization``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `MintTokenization`: TokenizationOperationResponse
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.MintTokenization`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const TokenizationMintTokenRequest =
    new CoboWaas2.TokenizationMintTokenRequest();
  apiInstance.mintTokenization(token_id, TokenizationMintTokenRequest).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Pause token contract
Source: https://cobo.com/developers/v2/api-references/tokenization/pause-token-contract

post /tokenization/tokens/{token_id}/pause
This operation pauses the token contract, temporarily halting token operations and transfers.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_operation_response import (
      TokenizationOperationResponse,
  )
  from cobo_waas2.models.tokenization_pause_token_request import (
      TokenizationPauseTokenRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      tokenization_pause_token_request = cobo_waas2.TokenizationPauseTokenRequest(
          source=cobo_waas2.TokenizationTokenOperationSource(
              cobo_waas2.TokenizationMpcOperationSource(
                  source_type="Org-Controlled",
                  wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                  address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
              )
          ),
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          ),
      )

      try:
          # Pause token contract
          api_response = api_instance.pause_tokenization(
              token_id, tokenization_pause_token_request=tokenization_pause_token_request
          )
          print("The response of TokenizationApi->pause_tokenization:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TokenizationApi->pause_tokenization: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      TokenizationPauseTokenRequest tokenizationPauseTokenRequest =
          new TokenizationPauseTokenRequest()
              .source(
                  new TokenizationTokenOperationSource(
                      new TokenizationMpcOperationSource()
                          .sourceType(TokenizationOperationSourceType.ORG_CONTROLLED)
                          .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                          .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")))
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        TokenizationOperationResponse result =
            apiInstance.pauseTokenization(tokenId, tokenizationPauseTokenRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#pauseTokenization");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	tokenizationPauseTokenRequest := *coboWaas2.NewTokenizationPauseTokenRequest(coboWaas2.TokenizationTokenOperationSource{TokenizationMpcOperationSource: coboWaas2.NewTokenizationMpcOperationSource(coboWaas2.TokenizationOperationSourceType("Org-Controlled"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")}, coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.PauseTokenization(ctx, tokenId).
  		TokenizationPauseTokenRequest(tokenizationPauseTokenRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `TokenizationAPI.PauseTokenization``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `PauseTokenization`: TokenizationOperationResponse
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.PauseTokenization`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const opts = {
    TokenizationPauseTokenRequest:
      CoboWaas2.TokenizationPauseTokenRequest.constructFromObject({
        source: {
          source_type: "Org-Controlled",
          wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
          address: "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
        },
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
      }),
  };
  apiInstance.pauseTokenization(token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Unpause token contract
Source: https://cobo.com/developers/v2/api-references/tokenization/unpause-token-contract

post /tokenization/tokens/{token_id}/unpause
This operation unpauses the token contract, resuming token operations and transfers.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_operation_response import (
      TokenizationOperationResponse,
  )
  from cobo_waas2.models.tokenization_unpause_token_request import (
      TokenizationUnpauseTokenRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      tokenization_unpause_token_request = cobo_waas2.TokenizationUnpauseTokenRequest(
          source=cobo_waas2.TokenizationTokenOperationSource(
              cobo_waas2.TokenizationMpcOperationSource(
                  source_type="Org-Controlled",
                  wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                  address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
              )
          ),
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          ),
      )

      try:
          # Unpause token contract
          api_response = api_instance.unpause_tokenization(
              token_id,
              tokenization_unpause_token_request=tokenization_unpause_token_request,
          )
          print("The response of TokenizationApi->unpause_tokenization:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TokenizationApi->unpause_tokenization: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      TokenizationUnpauseTokenRequest tokenizationUnpauseTokenRequest =
          new TokenizationUnpauseTokenRequest()
              .source(
                  new TokenizationTokenOperationSource(
                      new TokenizationMpcOperationSource()
                          .sourceType(TokenizationOperationSourceType.ORG_CONTROLLED)
                          .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                          .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")))
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        TokenizationOperationResponse result =
            apiInstance.unpauseTokenization(tokenId, tokenizationUnpauseTokenRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#unpauseTokenization");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	tokenizationUnpauseTokenRequest := *coboWaas2.NewTokenizationUnpauseTokenRequest(coboWaas2.TokenizationTokenOperationSource{TokenizationMpcOperationSource: coboWaas2.NewTokenizationMpcOperationSource(coboWaas2.TokenizationOperationSourceType("Org-Controlled"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")}, coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.UnpauseTokenization(ctx, tokenId).
  		TokenizationUnpauseTokenRequest(tokenizationUnpauseTokenRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.UnpauseTokenization``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UnpauseTokenization`: TokenizationOperationResponse
  	fmt.Fprintf(os.Stdout, "Response from `TokenizationAPI.UnpauseTokenization`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const opts = {
    TokenizationUnpauseTokenRequest:
      CoboWaas2.TokenizationUnpauseTokenRequest.constructFromObject({
        source: {
          source_type: "Org-Controlled",
          wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
          address: "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
        },
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
      }),
  };
  apiInstance.unpauseTokenization(token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Update addresses on allowlist
Source: https://cobo.com/developers/v2/api-references/tokenization/update-addresses-on-allowlist

post /tokenization/tokens/{token_id}/allowlist/addresses
This operation updates addresses on the allowlist.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_operation_response import (
      TokenizationOperationResponse,
  )
  from cobo_waas2.models.tokenization_update_allowlist_addresses_request import (
      TokenizationUpdateAllowlistAddressesRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      tokenization_update_allowlist_addresses_request = (
          cobo_waas2.TokenizationUpdateAllowlistAddressesRequest(
              action="Grant",
              source=cobo_waas2.TokenizationTokenOperationSource(
                  cobo_waas2.TokenizationMpcOperationSource(
                      source_type="Org-Controlled",
                      wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                      address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
                  )
              ),
              addresses=[
                  cobo_waas2.TokenizationUpdateAllowlistAddressesParamsAddressesInner(
                      address="0x789abc..."
                  ),
                  cobo_waas2.TokenizationUpdateAllowlistAddressesParamsAddressesInner(
                      address="0xdef012..."
                  ),
              ],
              fee=cobo_waas2.TransactionRequestFee(
                  cobo_waas2.TransactionRequestFixedFee(
                      fee_type="EVM_EIP_1559", token_id="TRON"
                  )
              ),
          )
      )

      try:
          # Update addresses on allowlist
          api_response = api_instance.update_tokenization_allowlist_addresses(
              token_id,
              tokenization_update_allowlist_addresses_request=tokenization_update_allowlist_addresses_request,
          )
          print(
              "The response of TokenizationApi->update_tokenization_allowlist_addresses:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->update_tokenization_allowlist_addresses: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      TokenizationUpdateAllowlistAddressesRequest tokenizationUpdateAllowlistAddressesRequest =
          new TokenizationUpdateAllowlistAddressesRequest()
              .action(TokenizationUpdateAddressAction.GRANT)
              .source(
                  new TokenizationTokenOperationSource(
                      new TokenizationMpcOperationSource()
                          .sourceType(TokenizationOperationSourceType.ORG_CONTROLLED)
                          .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                          .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")))
              .addresses(
                  Arrays.asList(
                      new TokenizationUpdateAllowlistAddressesParamsAddressesInner()
                          .address("0x789abc..."),
                      new TokenizationUpdateAllowlistAddressesParamsAddressesInner()
                          .address("0xdef012...")))
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        TokenizationOperationResponse result =
            apiInstance.updateTokenizationAllowlistAddresses(
                tokenId, tokenizationUpdateAllowlistAddressesRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling TokenizationApi#updateTokenizationAllowlistAddresses");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	tokenizationUpdateAllowlistAddressesRequest := *coboWaas2.NewTokenizationUpdateAllowlistAddressesRequest(coboWaas2.TokenizationUpdateAddressAction("Grant"), coboWaas2.TokenizationTokenOperationSource{TokenizationMpcOperationSource: coboWaas2.NewTokenizationMpcOperationSource(coboWaas2.TokenizationOperationSourceType("Org-Controlled"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")}, []coboWaas2.TokenizationUpdateAllowlistAddressesParamsAddressesInner{*coboWaas2.NewTokenizationUpdateAllowlistAddressesParamsAddressesInner("0x789abc...")}, coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.UpdateTokenizationAllowlistAddresses(ctx, tokenId).
  		TokenizationUpdateAllowlistAddressesRequest(tokenizationUpdateAllowlistAddressesRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.UpdateTokenizationAllowlistAddresses``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UpdateTokenizationAllowlistAddresses`: TokenizationOperationResponse
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TokenizationAPI.UpdateTokenizationAllowlistAddresses`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const opts = {
    TokenizationUpdateAllowlistAddressesRequest:
      CoboWaas2.TokenizationUpdateAllowlistAddressesRequest.constructFromObject({
        action: "Grant",
        source: {
          source_type: "Org-Controlled",
          wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
          address: "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
        },
        addresses: [
          { address: "0x789abc...", note: "reason for allowing" },
          { address: "0xdef012..." },
        ],
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
      }),
  };
  apiInstance.updateTokenizationAllowlistAddresses(token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Update addresses on blocklist
Source: https://cobo.com/developers/v2/api-references/tokenization/update-addresses-on-blocklist

post /tokenization/tokens/{token_id}/blocklist/addresses
This operation updates addresses on the blocklist.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_operation_response import (
      TokenizationOperationResponse,
  )
  from cobo_waas2.models.tokenization_update_blocklist_addresses_request import (
      TokenizationUpdateBlocklistAddressesRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      tokenization_update_blocklist_addresses_request = (
          cobo_waas2.TokenizationUpdateBlocklistAddressesRequest(
              action="Grant",
              source=cobo_waas2.TokenizationTokenOperationSource(
                  cobo_waas2.TokenizationMpcOperationSource(
                      source_type="Org-Controlled",
                      wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                      address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
                  )
              ),
              addresses=[
                  cobo_waas2.TokenizationUpdateBlocklistAddressesParamsAddressesInner(
                      address="0x789abc..."
                  ),
                  cobo_waas2.TokenizationUpdateBlocklistAddressesParamsAddressesInner(
                      address="0xdef012..."
                  ),
              ],
              fee=cobo_waas2.TransactionRequestFee(
                  cobo_waas2.TransactionRequestFixedFee(
                      fee_type="EVM_EIP_1559", token_id="TRON"
                  )
              ),
          )
      )

      try:
          # Update addresses on blocklist
          api_response = api_instance.update_tokenization_blocklist_addresses(
              token_id,
              tokenization_update_blocklist_addresses_request=tokenization_update_blocklist_addresses_request,
          )
          print(
              "The response of TokenizationApi->update_tokenization_blocklist_addresses:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->update_tokenization_blocklist_addresses: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      TokenizationUpdateBlocklistAddressesRequest tokenizationUpdateBlocklistAddressesRequest =
          new TokenizationUpdateBlocklistAddressesRequest()
              .action(TokenizationUpdateAddressAction.GRANT)
              .source(
                  new TokenizationTokenOperationSource(
                      new TokenizationMpcOperationSource()
                          .sourceType(TokenizationOperationSourceType.ORG_CONTROLLED)
                          .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                          .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")))
              .addresses(
                  Arrays.asList(
                      new TokenizationUpdateBlocklistAddressesParamsAddressesInner()
                          .address("0x789abc..."),
                      new TokenizationUpdateBlocklistAddressesParamsAddressesInner()
                          .address("0xdef012...")))
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        TokenizationOperationResponse result =
            apiInstance.updateTokenizationBlocklistAddresses(
                tokenId, tokenizationUpdateBlocklistAddressesRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling TokenizationApi#updateTokenizationBlocklistAddresses");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	tokenizationUpdateBlocklistAddressesRequest := *coboWaas2.NewTokenizationUpdateBlocklistAddressesRequest(coboWaas2.TokenizationUpdateAddressAction("Grant"), coboWaas2.TokenizationTokenOperationSource{TokenizationMpcOperationSource: coboWaas2.NewTokenizationMpcOperationSource(coboWaas2.TokenizationOperationSourceType("Org-Controlled"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")}, []coboWaas2.TokenizationUpdateBlocklistAddressesParamsAddressesInner{*coboWaas2.NewTokenizationUpdateBlocklistAddressesParamsAddressesInner("0x789abc...")}, coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.UpdateTokenizationBlocklistAddresses(ctx, tokenId).
  		TokenizationUpdateBlocklistAddressesRequest(tokenizationUpdateBlocklistAddressesRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.UpdateTokenizationBlocklistAddresses``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UpdateTokenizationBlocklistAddresses`: TokenizationOperationResponse
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TokenizationAPI.UpdateTokenizationBlocklistAddresses`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const opts = {
    TokenizationUpdateBlocklistAddressesRequest:
      CoboWaas2.TokenizationUpdateBlocklistAddressesRequest.constructFromObject({
        action: "Grant",
        source: {
          source_type: "Org-Controlled",
          wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
          address: "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
        },
        addresses: [
          { address: "0x789abc...", note: "reason for blocklisting" },
          { address: "0xdef012..." },
        ],
        fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
      }),
  };
  apiInstance.updateTokenizationBlocklistAddresses(token_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Update token permissions
Source: https://cobo.com/developers/v2/api-references/tokenization/update-token-permissions

post /tokenization/tokens/{token_id}/permissions
This operation updates permission settings for a tokenization contract.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tokenization_operation_response import (
      TokenizationOperationResponse,
  )
  from cobo_waas2.models.tokenization_update_permissions_request import (
      TokenizationUpdatePermissionsRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TokenizationApi(api_client)
      token_id = "ETH_USDT"
      tokenization_update_permissions_request = (
          cobo_waas2.TokenizationUpdatePermissionsRequest(
              source=cobo_waas2.TokenizationTokenOperationSource(
                  cobo_waas2.TokenizationMpcOperationSource(
                      source_type="Org-Controlled",
                      wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                      address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
                  )
              ),
              addresses=[
                  cobo_waas2.TokenizationUpdateAddressPermissions(
                      address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
                      action="add",
                      permissions=["MintTokens"],
                  )
              ],
              fee=cobo_waas2.TransactionRequestFee(
                  cobo_waas2.TransactionRequestFixedFee(
                      fee_type="EVM_EIP_1559", token_id="TRON"
                  )
              ),
          )
      )

      try:
          # Update token permissions
          api_response = api_instance.update_tokenization_permissions(
              token_id, tokenization_update_permissions_request
          )
          print("The response of TokenizationApi->update_tokenization_permissions:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TokenizationApi->update_tokenization_permissions: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TokenizationApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TokenizationApi apiInstance = new TokenizationApi();
      String tokenId = "ETH_USDT";
      TokenizationUpdatePermissionsRequest tokenizationUpdatePermissionsRequest =
          new TokenizationUpdatePermissionsRequest()
              .source(
                  new TokenizationTokenOperationSource(
                      new TokenizationMpcOperationSource()
                          .sourceType(TokenizationOperationSourceType.ORG_CONTROLLED)
                          .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                          .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")))
              .addresses(
                  Arrays.asList(
                      new TokenizationUpdateAddressPermissions()
                          .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")
                          .action(TokenizationPermissionAction.ADD)
                          .permissions(Arrays.asList(TokenizationTokenPermissionType.MINTTOKENS))))
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        TokenizationOperationResponse result =
            apiInstance.updateTokenizationPermissions(tokenId, tokenizationUpdatePermissionsRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TokenizationApi#updateTokenizationPermissions");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	tokenizationUpdatePermissionsRequest := *coboWaas2.NewTokenizationUpdatePermissionsRequest(coboWaas2.TokenizationTokenOperationSource{TokenizationMpcOperationSource: coboWaas2.NewTokenizationMpcOperationSource(coboWaas2.TokenizationOperationSourceType("Org-Controlled"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")}, []coboWaas2.TokenizationUpdateAddressPermissions{*coboWaas2.NewTokenizationUpdateAddressPermissions("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045", coboWaas2.TokenizationPermissionAction("add"), []coboWaas2.TokenizationTokenPermissionType{coboWaas2.TokenizationTokenPermissionType("ManagePermissions")})}, coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TokenizationAPI.UpdateTokenizationPermissions(ctx, tokenId).
  		TokenizationUpdatePermissionsRequest(tokenizationUpdatePermissionsRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TokenizationAPI.UpdateTokenizationPermissions``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `UpdateTokenizationPermissions`: TokenizationOperationResponse
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TokenizationAPI.UpdateTokenizationPermissions`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TokenizationApi();
  const token_id = "ETH_USDT";
  const TokenizationUpdatePermissionsRequest =
    new CoboWaas2.TokenizationUpdatePermissionsRequest();
  apiInstance
    .updateTokenizationPermissions(token_id, TokenizationUpdatePermissionsRequest)
    .then(
      (data) => {
        console.log("API called successfully. Returned data: " + data);
      },
      (error) => {
        console.error(error);
      },
    );

  ```
</RequestExample>


# Broadcast signed transactions
Source: https://cobo.com/developers/v2/api-references/transactions/broadcast-signed-transactions

post /transactions/broadcast
<Note>This operation is only applicable to the staking scenarios.</Note>
This operation broadcasts a list of signed transactions. 

If you set `auto_broadcast` to `false` when [creating a staking activity](https://www.cobo.com/developers/v2/api-references/stakings/create-stake-activity), the transaction will not be submitted to the blockchain automatically after being signed. In such cases, you can call this operation to broadcast the transaction to the blockchain.

A transaction can only be broadcast if its status is `Broadcasting`.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.broadcast_signed_transactions201_response_inner import (
      BroadcastSignedTransactions201ResponseInner,
  )
  from cobo_waas2.models.broadcast_signed_transactions_request import (
      BroadcastSignedTransactionsRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      broadcast_signed_transactions_request = (
          cobo_waas2.BroadcastSignedTransactionsRequest()
      )

      try:
          # Broadcast signed transactions
          api_response = api_instance.broadcast_signed_transactions(
              broadcast_signed_transactions_request=broadcast_signed_transactions_request
          )
          print("The response of TransactionsApi->broadcast_signed_transactions:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TransactionsApi->broadcast_signed_transactions: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      BroadcastSignedTransactionsRequest broadcastSignedTransactionsRequest =
          new BroadcastSignedTransactionsRequest();
      try {
        List<BroadcastSignedTransactions201ResponseInner> result =
            apiInstance.broadcastSignedTransactions(broadcastSignedTransactionsRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#broadcastSignedTransactions");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	broadcastSignedTransactionsRequest := *coboWaas2.NewBroadcastSignedTransactionsRequest()

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.BroadcastSignedTransactions(ctx).
  		BroadcastSignedTransactionsRequest(broadcastSignedTransactionsRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.BroadcastSignedTransactions``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `BroadcastSignedTransactions`: []BroadcastSignedTransactions201ResponseInner
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TransactionsAPI.BroadcastSignedTransactions`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const opts = {
    BroadcastSignedTransactionsRequest:
      new CoboWaas2.BroadcastSignedTransactionsRequest(),
  };
  apiInstance.broadcastSignedTransactions(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Call smart contract
Source: https://cobo.com/developers/v2/api-references/transactions/call-smart-contract

post /transactions/contract_call
This operation creates a transaction to interact with a smart contract on the blockchain.

You need to provide details such as the source address, destination address, and the calldata. You can specify the fee-related properties to limit the transaction fee. A transaction request for tracking is returned upon successful operation.

For smart contract call examples, you can refer to [Batch transfers using smart contracts](/v2/guides/transactions/batch-transfer) and [Swap tokens on Solana using Jupiter](/v2/guides/transactions/sol-jupiter-swap).

<Note>This operation uses `request_id` to prevent duplicate contract call requests. The `request_id` must be unique within the same organization. Duplicate requests with the same `request_id` will be rejected with an error and will not be executed again.</Note>

<Info>
Supported actions vary by blockchain:
- EVM chains — Support deploying contracts and calling contract functions.
- Solana — Supports calling contract functions only.
- TRON — Supports calling contract functions only.
- Stellar — Supports XLM trustline creation only.
- Cosmos — Supports initiating Cosmos native message-based transactions, such as transfers and staking operations.
</Info>

<Note>Currently, this operation only applies to transactions from Custodial Wallets (Web3 Wallets), MPC Wallets, or Smart Contract Wallets. Refer to the `destination` property for supported contract types.</Note>

<Info>If you initiate a transaction from a Smart Contract Wallet, a relevant transaction will be triggered from the Delegate to the Cobo Safe's address of the Smart Contract Wallet, with a transfer amount of <code>0</code>.</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.contract_call_params import ContractCallParams
  from cobo_waas2.models.create_transfer_transaction201_response import (
      CreateTransferTransaction201Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      contract_call_params = cobo_waas2.ContractCallParams(
          request_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
          chain_id="ETH",
          source=cobo_waas2.ContractCallSource(
              cobo_waas2.MpcContractCallSource(
                  source_type="Org-Controlled",
                  wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                  address="0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
              )
          ),
          destination=cobo_waas2.ContractCallDestination(
              cobo_waas2.EvmContractCallDestination(
                  destination_type="EVM_Contract",
                  address="0x0406db8351aa6839169bb363f63c2c808fee8f99",
                  calldata="0xa22cb4650000000000000000000000001e0049783f008a0085193e00003d00cd54003c71000000000000000000000000000000000000000000000000000000000000DEMO",
              )
          ),
      )

      try:
          # Call smart contract
          api_response = api_instance.create_contract_call_transaction(
              contract_call_params=contract_call_params
          )
          print("The response of TransactionsApi->create_contract_call_transaction:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TransactionsApi->create_contract_call_transaction: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      ContractCallParams contractCallParams =
          new ContractCallParams()
              .requestId("f47ac10b-58cc-4372-a567-0e02b2c3d479")
              .chainId("ETH")
              .source(
                  new ContractCallSource(
                      new MpcContractCallSource()
                          .sourceType(ContractCallSourceType.ORG_CONTROLLED)
                          .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                          .address("0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")))
              .destination(
                  new ContractCallDestination(
                      new EvmContractCallDestination()
                          .destinationType(ContractCallDestinationType.EVM_CONTRACT)
                          .address("0x0406db8351aa6839169bb363f63c2c808fee8f99")
                          .calldata(
                              "0xa22cb4650000000000000000000000001e0049783f008a0085193e00003d00cd54003c71000000000000000000000000000000000000000000000000000000000000DEMO")));
      try {
        CreateTransferTransaction201Response result =
            apiInstance.createContractCallTransaction(contractCallParams);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#createContractCallTransaction");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	contractCallParams := *coboWaas2.NewContractCallParams("f47ac10b-58cc-4372-a567-0e02b2c3d479", "ETH", coboWaas2.ContractCallSource{CustodialWeb3ContractCallSource: coboWaas2.NewCustodialWeb3ContractCallSource(coboWaas2.ContractCallSourceType("Web3"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045")}, coboWaas2.ContractCallDestination{CosmosContractCallDestination: coboWaas2.NewCosmosContractCallDestination(coboWaas2.ContractCallDestinationType("EVM_Contract"), []coboWaas2.CosmosContractCallMessage{*coboWaas2.NewCosmosContractCallMessage("/babylon.btcstaking.v1.MsgCreateBTCDelegation", "eyJ0eXBlIjoiYmFiY29zZS5idGNzdGFnaW5nLnYxLk1zZ0NyZWF0ZUJUQ0RlbGVnYXRpb24iLCJtZXNzYWdlIjp7ImNvbW1hbmRfaWQiOiJjb21tYW5kX2lkIiwibWVzc2FnZV92YWx1ZSI6Im1lc3NhZ2VfdmFsdWUiLCJtZXNzYWdlX3R5cGUiOiJtZXNzYWdlX3R5cGUifX0=")})})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.CreateContractCallTransaction(ctx).
  		ContractCallParams(contractCallParams).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.CreateContractCallTransaction``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateContractCallTransaction`: CreateTransferTransaction201Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TransactionsAPI.CreateContractCallTransaction`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const opts = {
    ContractCallParams: CoboWaas2.ContractCallParams.constructFromObject({
      request_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
      chain_id: "ETH",
      source: {
        source_type: "Org-Controlled",
        wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
        address: "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
      },
      destination: {
        destination_type: "EVM_Contract",
        address: "0x0406db8351aa6839169bb363f63c2c808fee8f99",
        calldata:
          "0xa22cb4650000000000000000000000001e0049783f008a0085193e00003d00cd54003c71000000000000000000000000000000000000000000000000000000000000DEMO",
      },
    }),
  };
  apiInstance.createContractCallTransaction(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Cancel transaction
Source: https://cobo.com/developers/v2/api-references/transactions/cancel-transaction

post /transactions/{transaction_id}/cancel
This operation cancels a specified transaction. Canceling a transaction stops it while it is still pending. For more information, see [Cancel a transaction](https://www.cobo.com/developers/v2/guides/transactions/manage-transactions#cancel-a-transaction).

<Note>This operation only applies to transactions from MPC Wallets and Smart Contract Wallets.</Note>

A transaction can be cancelled if its status is either of the following:
- `Submitted`
- `PendingScreening`
- `PendingAuthorization`
- `PendingSignature` (Only when the sub-status is `Queue`, `InsufficientBalance`, `InsufficientBalanceFundLocked`, `PendingSignerApproval`, `PendingSystemProcessing`, or `Built`)


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_transfer_transaction201_response import (
      CreateTransferTransaction201Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Cancel transaction
          api_response = api_instance.cancel_transaction_by_id(transaction_id)
          print("The response of TransactionsApi->cancel_transaction_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TransactionsApi->cancel_transaction_by_id: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      UUID transactionId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        CreateTransferTransaction201Response result =
            apiInstance.cancelTransactionById(transactionId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#cancelTransactionById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.CancelTransactionById(ctx, transactionId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.CancelTransactionById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CancelTransactionById`: CreateTransferTransaction201Response
  	fmt.Fprintf(os.Stdout, "Response from `TransactionsAPI.CancelTransactionById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.cancelTransactionById(transaction_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Check Cobo Loop transfers
Source: https://cobo.com/developers/v2/api-references/transactions/check-cobo-loop-transfers

get /transactions/check_loop_transfers
This operation verifies if the transactions from a given source wallet to a list of given destinations can be executed as Cobo Loop transfers. 

For more information about Cobo Loop, see [Cobo Loop's product manuals](https://manuals.cobo.com/en/portal/custodial-wallets/cobo-loop).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.check_loop_transfers200_response_inner import (
      CheckLoopTransfers200ResponseInner,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      token_id = "ETH_USDT"
      source_wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      destination_addresses = "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97"

      try:
          # Check Cobo Loop transfers
          api_response = api_instance.check_loop_transfers(
              token_id, source_wallet_id, destination_addresses
          )
          print("The response of TransactionsApi->check_loop_transfers:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TransactionsApi->check_loop_transfers: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      String tokenId = "ETH_USDT";
      UUID sourceWalletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String destinationAddresses =
          "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97";
      try {
        List<CheckLoopTransfers200ResponseInner> result =
            apiInstance.checkLoopTransfers(tokenId, sourceWalletId, destinationAddresses);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#checkLoopTransfers");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	tokenId := "ETH_USDT"
  	sourceWalletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	destinationAddresses := "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.CheckLoopTransfers(ctx).
  		TokenId(tokenId).
  		SourceWalletId(sourceWalletId).
  		DestinationAddresses(destinationAddresses).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.CheckLoopTransfers``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CheckLoopTransfers`: []CheckLoopTransfers200ResponseInner
  	fmt.Fprintf(os.Stdout, "Response from `TransactionsAPI.CheckLoopTransfers`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const token_id = "ETH_USDT";
  const source_wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const destination_addresses =
    "0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,0x4838B106FCe9647Bdf1E7877BF73cE8B0BAD5f97";
  apiInstance
    .checkLoopTransfers(token_id, source_wallet_id, destination_addresses)
    .then(
      (data) => {
        console.log("API called successfully. Returned data: " + data);
      },
      (error) => {
        console.error(error);
      },
    );

  ```
</RequestExample>


# Drop transaction
Source: https://cobo.com/developers/v2/api-references/transactions/drop-transaction

post /transactions/{transaction_id}/drop
This operation drops a specified transaction. Dropping a transaction leverages RBF to replace the original transaction with a version that effectively cancels it. For more details about dropping a transaction, refer to [Drop a transaction](https://www.cobo.com/developers/v2/guides/transactions/manage-transactions#drop-a-transaction).

A transaction can be dropped only if its status is `Broadcasting`.

<Note>This operation only applies to transactions from Custodial Wallets (Web3 Wallets), MPC Wallets and Smart Contract Wallets. It does not apply to transactions on the following chains: VET, TRON, TVET, SOL, and TON.</Note>

You can use the `address` or `included_utxos` properties in the request body to specify the address or UTXOs that will cover the transaction fee. Generally, the transaction fee is paid by the original transaction's source. If that source's balance is insufficient, the specified address or UTXOs can be used to cover the fee.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_transfer_transaction201_response import (
      CreateTransferTransaction201Response,
  )
  from cobo_waas2.models.transaction_rbf import TransactionRbf
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      transaction_rbf = cobo_waas2.TransactionRbf(
          request_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          ),
      )

      try:
          # Drop transaction
          api_response = api_instance.drop_transaction_by_id(
              transaction_id, transaction_rbf=transaction_rbf
          )
          print("The response of TransactionsApi->drop_transaction_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TransactionsApi->drop_transaction_by_id: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      UUID transactionId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      TransactionRbf transactionRbf =
          new TransactionRbf()
              .requestId("f47ac10b-58cc-4372-a567-0e02b2c3d479")
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        CreateTransferTransaction201Response result =
            apiInstance.dropTransactionById(transactionId, transactionRbf);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#dropTransactionById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	transactionRbf := *coboWaas2.NewTransactionRbf("f47ac10b-58cc-4372-a567-0e02b2c3d479", coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.DropTransactionById(ctx, transactionId).
  		TransactionRbf(transactionRbf).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.DropTransactionById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `DropTransactionById`: CreateTransferTransaction201Response
  	fmt.Fprintf(os.Stdout, "Response from `TransactionsAPI.DropTransactionById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    TransactionRbf: CoboWaas2.TransactionRbf.constructFromObject({
      request_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
      fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
    }),
  };
  apiInstance.dropTransactionById(transaction_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Estimate transaction fee
Source: https://cobo.com/developers/v2/api-references/transactions/estimate-transaction-fee

post /transactions/estimate_fee
This operation estimates the transaction fee of a token transfer or a contract call based on the fee model that the chain uses, considering factors such as network congestion and transaction complexity.

You need to specify the transaction information, including the request ID, request type, source address, destination address, token ID (only applicable to token transfers), and chain ID (only applicable to contract calls).

The response can contain different properties based on the transaction fee model used by the chain. For the legacy, EIP-1559, and UTXO fee models, Cobo also supports three different transaction speed levels: slow, recommended, and fast. For more information about estimating transaction fees, refer to [Estimate transaction fee](https://www.cobo.com/developers/v2/guides/transactions/estimate-fees).

<Note>Fee estimates are point-in-time and short-lived. Because on-chain gas prices change continuously, re-estimate the fee immediately before submitting a withdrawal. Submitting a transaction based on a stale estimate may cause the transaction to be rejected because the fee is insufficient.</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.estimate_fee_params import EstimateFeeParams
  from cobo_waas2.models.estimated_fee import EstimatedFee
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      estimate_fee_params = cobo_waas2.EstimateFeeParams(
          cobo_waas2.EstimateTransferFeeParams(
              request_type="Transfer",
              source=cobo_waas2.TransferSource(
                  cobo_waas2.CustodialTransferSource(
                      source_type="Asset",
                      wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                  )
              ),
              token_id="TRON_USDT",
              destination = cobo_waas2.TransferDestination(
                  cobo_waas2.AddressTransferDestination(
                      destination_type = "Address",
                      account_output = cobo_waas2.AddressTransferDestinationAccountOutput(
                          address = "19AR6YWEGbSoY8UT9Ksy9WrmrZPD5sL4Ku",
                          amount = "1.5"
                      )
                  )
              ),
              fee_type = "Fixed"
          )
      )

      try:
          # Estimate transaction fee
          api_response = api_instance.estimate_fee(
              estimate_fee_params=estimate_fee_params
          )
          print("The response of TransactionsApi->estimate_fee:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TransactionsApi->estimate_fee: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      EstimateFeeParams estimateFeeParams =
          new EstimateFeeParams(
              new EstimateTransferFeeParams()
                  .requestType(EstimateFeeRequestType.TRANSFER)
                  .source(
                      new TransferSource(
                          new CustodialTransferSource()
                              .sourceType(WalletSubtype.ASSET)
                              .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))))
                  .tokenId("TRON_USDT")
                  .destination(
                      new TransferDestination(
                          new AddressTransferDestination()
                              .destinationType(TransferDestinationType.ADDRESS)
                              .accountOutput(
                                new AddressTransferDestinationAccountOutput()
                                    .address("19AR6YWEGbSoY8UT9Ksy9WrmrZPD5sL4Ku")
                                    .amount("1.5")
                          )
                      )
                  )
                  .feeType(FeeType.FIXED)
            );
      try {
        EstimatedFee result = apiInstance.estimateFee(estimateFeeParams);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#estimateFee");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	estimateFeeParams := coboWaas2.EstimateFeeParams{
  		EstimateContractCallFeeParams: coboWaas2.NewEstimateContractCallFeeParams(
  			coboWaas2.EstimateFeeRequestType("Transfer"),
  			"ETH",
  			coboWaas2.ContractCallSource{
  				CustodialWeb3ContractCallSource: coboWaas2.NewCustodialWeb3ContractCallSource(
  					coboWaas2.ContractCallSourceType("Web3"),
  					"f47ac10b-58cc-4372-a567-0e02b2c3d479",
  					"0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045",
  				),
  			},
  		),
  	}

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.EstimateFee(ctx).
  		EstimateFeeParams(estimateFeeParams).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `TransactionsAPI.EstimateFee``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `EstimateFee`: EstimatedFee
  	fmt.Fprintf(os.Stdout, "Response from `TransactionsAPI.EstimateFee`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const opts = {
    EstimateFeeParams: CoboWaas2.EstimateFeeParams.constructFromObject({
      request_type: "Transfer",
      source: {
        source_type: "Asset",
        wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
      },
      token_id: "ETH_USDT",
      "destination": {
        "destination_type": "Address",
        "account_output": {
          "address": "19AR6YWEGbSoY8UT9Ksy9WrmrZPD5sL4Ku",
          "memo": "",
          "amount": "0.1"
        }
      },
      "fee_type": "Fixed"
    }),
  };
  apiInstance.estimateFee(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get transaction information
Source: https://cobo.com/developers/v2/api-references/transactions/get-transaction-information

get /transactions/{transaction_id}
This operation retrieves detailed information about a specified transaction, such as the transaction status, source address, destination address, and timestamp.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.transaction_detail import TransactionDetail
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get transaction information
          api_response = api_instance.get_transaction_by_id(transaction_id)
          print("The response of TransactionsApi->get_transaction_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TransactionsApi->get_transaction_by_id: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      UUID transactionId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        TransactionDetail result = apiInstance.getTransactionById(transactionId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#getTransactionById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.GetTransactionById(ctx, transactionId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.GetTransactionById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetTransactionById`: TransactionDetail
  	fmt.Fprintf(os.Stdout, "Response from `TransactionsAPI.GetTransactionById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getTransactionById(transaction_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List all transactions
Source: https://cobo.com/developers/v2/api-references/transactions/list-all-transactions

get /transactions
This operation retrieves all the transactions under your organization.

You can filter the results by request ID, Cobo ID, transaction ID, transaction hash, type, status, and timestamps. You can also paginate and sort your query results.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_transactions200_response import ListTransactions200Response
  from cobo_waas2.models.wallet_subtype import WalletSubtype
  from cobo_waas2.models.wallet_type import WalletType
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      request_id = "web_send_by_user_327_1610444045047"
      cobo_ids = "20231213122855000000000000000000,20231213122955000000000000000000"
      transaction_ids = (
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3"
      )
      transaction_hashes = (
          "239861be9a4afe080c359b7fe4a1d035945ec46256b1a0f44d1267c71de8ec28"
      )
      types = "Deposit,Withdrawal"
      statuses = "Completed,Failed"
      wallet_ids = (
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,1ddca562-8434-41c9-8809-d437bad9c868"
      )
      chain_ids = "BTC,ETH"
      token_ids = "ETH_USDT,ETH_USDC"
      asset_ids = "USDT,USDC"
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      wallet_type = cobo_waas2.WalletType("Custodial")
      wallet_subtype = cobo_waas2.WalletSubtype("Asset")
      project_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      min_created_timestamp = 1635744000000
      max_created_timestamp = 1635744000000
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
      direction = "ASC"

      try:
          # List all transactions
          api_response = api_instance.list_transactions(
              request_id=request_id,
              cobo_ids=cobo_ids,
              transaction_ids=transaction_ids,
              transaction_hashes=transaction_hashes,
              types=types,
              statuses=statuses,
              wallet_ids=wallet_ids,
              chain_ids=chain_ids,
              token_ids=token_ids,
              asset_ids=asset_ids,
              vault_id=vault_id,
              wallet_type=wallet_type,
              wallet_subtype=wallet_subtype,
              project_id=project_id,
              min_created_timestamp=min_created_timestamp,
              max_created_timestamp=max_created_timestamp,
              limit=limit,
              before=before,
              after=after,
              direction=direction,
          )
          print("The response of TransactionsApi->list_transactions:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TransactionsApi->list_transactions: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      String requestId = "web_send_by_user_327_1610444045047";
      String coboIds = "20231213122855000000000000000000,20231213122955000000000000000000";
      String transactionIds =
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3";
      String transactionHashes = "239861be9a4afe080c359b7fe4a1d035945ec46256b1a0f44d1267c71de8ec28";
      String types = "Deposit,Withdrawal";
      String statuses = "Completed,Failed";
      String walletIds = "f47ac10b-58cc-4372-a567-0e02b2c3d479,1ddca562-8434-41c9-8809-d437bad9c868";
      String chainIds = "BTC,ETH";
      String tokenIds = "ETH_USDT,ETH_USDC";
      String assetIds = "USDT,USDC";
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      WalletType walletType = WalletType.fromValue("Custodial");
      WalletSubtype walletSubtype = WalletSubtype.fromValue("Asset");
      UUID projectId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      Long minCreatedTimestamp = 1635744000000L;
      Long maxCreatedTimestamp = 1635744000000L;
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      String direction = "ASC";
      try {
        ListTransactions200Response result =
            apiInstance.listTransactions(
                requestId,
                coboIds,
                transactionIds,
                transactionHashes,
                types,
                statuses,
                walletIds,
                chainIds,
                tokenIds,
                assetIds,
                vaultId,
                walletType,
                walletSubtype,
                projectId,
                minCreatedTimestamp,
                maxCreatedTimestamp,
                limit,
                before,
                after,
                direction);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#listTransactions");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	requestId := "web_send_by_user_327_1610444045047"
  	coboIds := "20231213122855000000000000000000,20231213122955000000000000000000"
  	transactionIds := "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3"
  	transactionHashes := "239861be9a4afe080c359b7fe4a1d035945ec46256b1a0f44d1267c71de8ec28"
  	types := "Deposit,Withdrawal"
  	statuses := "Completed,Failed"
  	walletIds := "f47ac10b-58cc-4372-a567-0e02b2c3d479,1ddca562-8434-41c9-8809-d437bad9c868"
  	chainIds := "BTC,ETH"
  	tokenIds := "ETH_USDT,ETH_USDC"
  	assetIds := "USDT,USDC"
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	walletType := coboWaas2.WalletType("Custodial")
  	walletSubtype := coboWaas2.WalletSubtype("Asset")
  	projectId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	minCreatedTimestamp := int64(1635744000000)
  	maxCreatedTimestamp := int64(1635744000000)
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"
  	direction := "ASC"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.ListTransactions(ctx).
  		RequestId(requestId).
  		CoboIds(coboIds).
  		TransactionIds(transactionIds).
  		TransactionHashes(transactionHashes).
  		Types(types).
  		Statuses(statuses).
  		WalletIds(walletIds).
  		ChainIds(chainIds).
  		TokenIds(tokenIds).
  		AssetIds(assetIds).
  		VaultId(vaultId).
  		WalletType(walletType).
  		WalletSubtype(walletSubtype).
  		ProjectId(projectId).
  		MinCreatedTimestamp(minCreatedTimestamp).
  		MaxCreatedTimestamp(maxCreatedTimestamp).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Direction(direction).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `TransactionsAPI.ListTransactions``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTransactions`: ListTransactions200Response
  	fmt.Fprintf(os.Stdout, "Response from `TransactionsAPI.ListTransactions`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const opts = {
    request_id: "web_send_by_user_327_1610444045047",
    cobo_ids: "20231213122855000000000000000000,20231213122955000000000000000000",
    transaction_ids:
      "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3",
    transaction_hashes:
      "239861be9a4afe080c359b7fe4a1d035945ec46256b1a0f44d1267c71de8ec28",
    types: "Deposit,Withdrawal",
    statuses: "Completed,Failed",
    wallet_ids:
      "f47ac10b-58cc-4372-a567-0e02b2c3d479,1ddca562-8434-41c9-8809-d437bad9c868",
    chain_ids: "BTC,ETH",
    token_ids: "ETH_USDT,ETH_USDC",
    asset_ids: "USDT,USDC",
    vault_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
    wallet_type: "Custodial",
    wallet_subtype: "Asset",
    project_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
    min_created_timestamp: 1635744000000,
    max_created_timestamp: 1635744000000,
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
    direction: "ASC",
  };
  apiInstance.listTransactions(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List approval details
Source: https://cobo.com/developers/v2/api-references/transactions/list-approval-details

get /transactions/approval/details
This operation retrieves comprehensive approval information for transactions, including approval status, reviewer details, signatures, and approval history. You can filter the results by transaction IDs, Cobo IDs, or request IDs. 

This operation is commonly used to monitor approval progress and identify delays in multi-signature workflows.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.approval_detail import ApprovalDetail
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      transaction_ids = (
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3"
      )
      cobo_ids = "20231213122855000000000000000000,20231213122955000000000000000000"
      request_ids = (
          "web_send_by_user_327_1610444045047,web_send_by_user_327_1610444045048"
      )

      try:
          # List approval details
          api_response = api_instance.list_approval_details(
              transaction_ids=transaction_ids, cobo_ids=cobo_ids, request_ids=request_ids
          )
          print("The response of TransactionsApi->list_approval_details:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TransactionsApi->list_approval_details: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      String transactionIds =
          "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3";
      String coboIds = "20231213122855000000000000000000,20231213122955000000000000000000";
      String requestIds = "web_send_by_user_327_1610444045047,web_send_by_user_327_1610444045048";
      try {
        List<ApprovalDetail> result =
            apiInstance.listApprovalDetails(transactionIds, coboIds, requestIds);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#listApprovalDetails");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionIds := "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3"
  	coboIds := "20231213122855000000000000000000,20231213122955000000000000000000"
  	requestIds := "web_send_by_user_327_1610444045047,web_send_by_user_327_1610444045048"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.ListApprovalDetails(ctx).
  		TransactionIds(transactionIds).
  		CoboIds(coboIds).
  		RequestIds(requestIds).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.ListApprovalDetails``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListApprovalDetails`: []ApprovalDetail
  	fmt.Fprintf(os.Stdout, "Response from `TransactionsAPI.ListApprovalDetails`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const opts = {
    transaction_ids:
      "f47ac10b-58cc-4372-a567-0e02b2c3d479,557918d2-632a-4fe1-932f-315711f05fe3",
    cobo_ids: "20231213122855000000000000000000,20231213122955000000000000000000",
    request_ids:
      "web_send_by_user_327_1610444045047,web_send_by_user_327_1610444045048",
  };
  apiInstance.listApprovalDetails(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List transaction templates
Source: https://cobo.com/developers/v2/api-references/transactions/list-transaction-templates

get /transactions/templates
This operation retrieves approval templates based on the specified template key and template version.

These templates define the content used to generate approval messages displayed to users, including messages for transaction approvals and other approval workflows.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.approval_template import ApprovalTemplate
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      template_key = "withdrawal"
      template_version = "1.0.0"

      try:
          # List transaction templates
          api_response = api_instance.list_transaction_templates(
              template_key, template_version=template_version
          )
          print("The response of TransactionsApi->list_transaction_templates:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TransactionsApi->list_transaction_templates: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      String templateKey = "withdrawal";
      String templateVersion = "1.0.0";
      try {
        List<ApprovalTemplate> result =
            apiInstance.listTransactionTemplates(templateKey, templateVersion);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#listTransactionTemplates");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	templateKey := "withdrawal"
  	templateVersion := "1.0.0"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.ListTransactionTemplates(ctx).
  		TemplateKey(templateKey).
  		TemplateVersion(templateVersion).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.ListTransactionTemplates``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListTransactionTemplates`: []ApprovalTemplate
  	fmt.Fprintf(os.Stdout, "Response from `TransactionsAPI.ListTransactionTemplates`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const template_key = "withdrawal";
  const opts = {
    template_version: "1.0.0",
  };
  apiInstance.listTransactionTemplates(template_key, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Sign and broadcast transaction
Source: https://cobo.com/developers/v2/api-references/transactions/sign-and-broadcast-transaction

post /transactions/{transaction_id}/sign_and_broadcast
This operation signs and broadcasts a specified transaction.

To call this operation, the following conditions must be met:
- The `transaction_process_type` of the transaction must be set to `BuildOnly` when you call the [Transfer token](https://www.cobo.com/developers/v2/api-references/transactions/transfer-token) or [Call smart contract](https://www.cobo.com/developers/v2/api-references/transactions/call-smart-contract) operation.  
- The transaction status must be `Built`.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_transfer_transaction201_response import (
      CreateTransferTransaction201Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Sign and broadcast transaction
          api_response = api_instance.sign_and_broadcast_transaction_by_id(transaction_id)
          print(
              "The response of TransactionsApi->sign_and_broadcast_transaction_by_id:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TransactionsApi->sign_and_broadcast_transaction_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      UUID transactionId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        CreateTransferTransaction201Response result =
            apiInstance.signAndBroadcastTransactionById(transactionId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#signAndBroadcastTransactionById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.SignAndBroadcastTransactionById(ctx, transactionId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.SignAndBroadcastTransactionById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `SignAndBroadcastTransactionById`: CreateTransferTransaction201Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TransactionsAPI.SignAndBroadcastTransactionById`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.signAndBroadcastTransactionById(transaction_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Sign message
Source: https://cobo.com/developers/v2/api-references/transactions/sign-message

post /transactions/message_sign
This operation creates a transaction to sign the provided message using cryptographic techniques.

In some scenarios, you want to sign a message for identity authentication or transaction approval. You need to provide details such as the source address, destination address, and the message to be signed. A transaction request for tracking is returned upon successful operation.

You can get the signature result by calling [Get transaction information](https://www.cobo.com/developers/v2/api-references/transactions/get-transaction-information). 

<Note>
This operation only supports message signing transactions from the following wallets and chains:
- MPC Wallets: BTC, EVM-compatible chains, and Cosmos.  
- Custodial Wallets (Web3 Wallets): EVM-compatible chains.
</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_transfer_transaction201_response import (
      CreateTransferTransaction201Response,
  )
  from cobo_waas2.models.message_sign_params import MessageSignParams
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      message_sign_params = cobo_waas2.MessageSignParams(
          request_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
          chain_id="ETH",
          source=cobo_waas2.MessageSignSource(
              cobo_waas2.MpcMessageSignSource(
                  source_type="Org-Controlled",
                  wallet_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
                  address="19AR6YWEGbSoY8UT9Ksy9WrmrZPD5sL4Ku",
              )
          ),
          destination=cobo_waas2.MessageSignDestination(
              cobo_waas2.EvmEIP191MessageSignDestination(
                  destination_type="EVM_EIP_191_Signature", message="YWFhYQ=="
              )
          ),
      )

      try:
          # Sign message
          api_response = api_instance.create_message_sign_transaction(
              message_sign_params=message_sign_params
          )
          print("The response of TransactionsApi->create_message_sign_transaction:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TransactionsApi->create_message_sign_transaction: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      MessageSignParams messageSignParams =
          new MessageSignParams()
              .requestId("f47ac10b-58cc-4372-a567-0e02b2c3d479")
              .chainId("ETH")
              .source(
                  new MessageSignSource(
                      new MpcMessageSignSource()
                          .sourceType(MessageSignSourceType.ORG_CONTROLLED)
                          .walletId(UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479"))
                          .address("19AR6YWEGbSoY8UT9Ksy9WrmrZPD5sL4Ku")))
              .destination(
                  new MessageSignDestination(
                      new EvmEIP191MessageSignDestination()
                          .destinationType(MessageSignDestinationType.EVM_EIP_191_SIGNATURE)
                          .message("YWFhYQ==")));
      try {
        CreateTransferTransaction201Response result =
            apiInstance.createMessageSignTransaction(messageSignParams);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#createMessageSignTransaction");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	messageSignParams := *coboWaas2.NewMessageSignParams("f47ac10b-58cc-4372-a567-0e02b2c3d479", "ETH", coboWaas2.MessageSignSource{CustodialWeb3MessageSignSource: coboWaas2.NewCustodialWeb3MessageSignSource(coboWaas2.MessageSignSourceType("Web3"), "f47ac10b-58cc-4372-a567-0e02b2c3d479", "19AR6YWEGbSoY8UT9Ksy9WrmrZPD5sL4Ku")}, coboWaas2.MessageSignDestination{BTCBIP137MessageSignDestination: coboWaas2.NewBTCBIP137MessageSignDestination(coboWaas2.MessageSignDestinationType("EVM_EIP_191_Signature"), "MessageBip137_example")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.CreateMessageSignTransaction(ctx).
  		MessageSignParams(messageSignParams).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.CreateMessageSignTransaction``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateMessageSignTransaction`: CreateTransferTransaction201Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `TransactionsAPI.CreateMessageSignTransaction`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const opts = {
    MessageSignParams: CoboWaas2.MessageSignParams.constructFromObject({
      request_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
      chain_id: "ETH",
      source: {
        source_type: "Org-Controlled",
        wallet_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
        address: "19AR6YWEGbSoY8UT9Ksy9WrmrZPD5sL4Ku",
      },
      destination: {
        destination_type: "EVM_EIP_191_Signature",
        message: "YWFhYQ==",
      },
    }),
  };
  apiInstance.createMessageSignTransaction(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Speed up transaction
Source: https://cobo.com/developers/v2/api-references/transactions/speed-up-transaction

post /transactions/{transaction_id}/speedup
This operation accelerates a specified transaction. Speeding up a transaction will trigger a Replace-By-Fee (RBF) transaction which is a new version of the original transaction. For more details about speeding up a transaction, refer to [Speed up a transaction](https://www.cobo.com/developers/v2/guides/transactions/manage-transactions#speed-up-a-transaction).

You can use the `address` or `included_utxos` properties in the request body to specify the address or UTXOs that will cover the transaction fee. Generally, the transaction fee is paid by the original transaction's source. If that source's balance is insufficient, the specified address or UTXOs can be used to cover the fee.

A transaction can be sped up only if its status is `Broadcasting`.

<Note>This operation only applies to transactions from Custodial Wallets (Web3 Wallets), MPC Wallets and Smart Contract Wallets. It does not apply to transactions on the following chains: VET, TRON, TVET, SOL, and TON.</Note>

<Info>If you speed up a transaction from a Smart Contract Wallet, two RBF transactions will be triggered, one for the transaction from the Smart Contract Wallet, and the other for the transaction from the Delegate.</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_transfer_transaction201_response import (
      CreateTransferTransaction201Response,
  )
  from cobo_waas2.models.transaction_rbf import TransactionRbf
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      transaction_rbf = cobo_waas2.TransactionRbf(
          request_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
          fee=cobo_waas2.TransactionRequestFee(
              cobo_waas2.TransactionRequestFixedFee(
                  fee_type="EVM_EIP_1559", token_id="TRON"
              )
          ),
      )

      try:
          # Speed up transaction
          api_response = api_instance.speedup_transaction_by_id(
              transaction_id, transaction_rbf=transaction_rbf
          )
          print("The response of TransactionsApi->speedup_transaction_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TransactionsApi->speedup_transaction_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      UUID transactionId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      TransactionRbf transactionRbf =
          new TransactionRbf()
              .requestId("f47ac10b-58cc-4372-a567-0e02b2c3d479")
              .fee(
                  new TransactionRequestFee(
                      new TransactionRequestFixedFee()
                          .feeType(FeeType.EVM_EIP_1559)
                          .tokenId("TRON")));
      try {
        CreateTransferTransaction201Response result =
            apiInstance.speedupTransactionById(transactionId, transactionRbf);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#speedupTransactionById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	transactionRbf := *coboWaas2.NewTransactionRbf("f47ac10b-58cc-4372-a567-0e02b2c3d479", coboWaas2.TransactionRequestFee{TransactionRequestEvmEip1559Fee: coboWaas2.NewTransactionRequestEvmEip1559Fee("9000000000000", "1000000000000", coboWaas2.FeeType("Fixed"), "ETH")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.SpeedupTransactionById(ctx, transactionId).
  		TransactionRbf(transactionRbf).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.SpeedupTransactionById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `SpeedupTransactionById`: CreateTransferTransaction201Response
  	fmt.Fprintf(os.Stdout, "Response from `TransactionsAPI.SpeedupTransactionById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const transaction_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    TransactionRbf: CoboWaas2.TransactionRbf.constructFromObject({
      request_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
      fee: { fee_type: "EVM_EIP_1559", token_id: "TRON" },
    }),
  };
  apiInstance.speedupTransactionById(transaction_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Transfer token
Source: https://cobo.com/developers/v2/api-references/transactions/transfer-token

post /transactions/transfer
The operation transfers your assets from a wallet created on Cobo Portal to another address.

You need to specify details such as the sender address and recipient address, token ID, and the amount to transfer. You can specify the fee-related properties to limit the transaction fee. A transaction request for tracking is returned upon successful operation.

<Note>This operation uses `request_id` to prevent duplicate transfer requests. The `request_id` must be unique within the same organization. Duplicate requests with the same `request_id` will be rejected with an error and will not be executed again.</Note>

<Note>If you make transfers from Custodial Wallets (Asset Wallets) and Exchange Wallets, do not set the fee-related properties, as they will not take effects.</Note>

<Note>You can transfer tokens to multiple addresses only if you use MPC Wallets as the transaction source. To do this, you should use the <code>utxo_outputs</code> property to specify the destination addresses.</Note>

<Info>If you initiate a transaction from a Smart Contract Wallet, a relevant transaction will be triggered from the Delegate to the Cobo Safe's address of the Smart Contract Wallet, with a transfer amount of <code>0</code>.</Info>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_transfer_transaction201_response import (
      CreateTransferTransaction201Response,
  )
  from cobo_waas2.models.transfer_params import TransferParams
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TransactionsApi(api_client)
      transfer_params = cobo_waas2.TransferParams(
          request_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
          source=cobo_waas2.TransferSource(
              cobo_waas2.CustodialTransferSource(
                  source_type="Asset", wallet_id="d3fcfaef-f415-4210-9e5c-fbed0e090495"
              )
          ),
          token_id="ETH_USDT",
          destination=cobo_waas2.TransferDestination(
              cobo_waas2.AddressTransferDestination(destination_type="Address", account_output=cobo_waas2.AddressTransferDestinationAccountOutput(address="19AR6YWEGbSoY8UT9Ksy9WrmrZPD5sL4Ku",amount="1.5"))
          ),
      )

      try:
          # Transfer token
          api_response = api_instance.create_transfer_transaction(
              transfer_params=transfer_params
          )
          print("The response of TransactionsApi->create_transfer_transaction:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TransactionsApi->create_transfer_transaction: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TransactionsApi;
  import com.cobo.waas2.model.*;
  import java.util.UUID;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TransactionsApi apiInstance = new TransactionsApi();
      TransferParams transferParams =
          new TransferParams()
              .requestId("f47ac10b-58cc-4372-a567-0e02b2c3d479")
              .source(
                  new TransferSource(
                      new CustodialTransferSource()
                          .sourceType(WalletSubtype.ASSET)
                          .walletId(UUID.fromString("d3fcfaef-f415-4210-9e5c-fbed0e090495"))))
              .tokenId("ETH_USDT")
              .destination(
                  new TransferDestination(
                      new AddressTransferDestination()
                          .destinationType(TransferDestinationType.ADDRESS)
                          .accountOutput(
                              new AddressTransferDestinationAccountOutput()
                                  .address("19AR6YWEGbSoY8UT9Ksy9WrmrZPD5sL4Ku")
                                  .amount("1.5"))));
      try {
        CreateTransferTransaction201Response result =
            apiInstance.createTransferTransaction(transferParams);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TransactionsApi#createTransferTransaction");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transferParams := *coboWaas2.NewTransferParams("f47ac10b-58cc-4372-a567-0e02b2c3d479", coboWaas2.TransferSource{CustodialTransferSource: coboWaas2.NewCustodialTransferSource(coboWaas2.WalletSubtype("Asset"), "d3fcfaef-f415-4210-9e5c-fbed0e090495")}, "ETH_USDT", coboWaas2.TransferDestination{AddressTransferDestination: coboWaas2.NewAddressTransferDestination(coboWaas2.TransferDestinationType("Address"))})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TransactionsAPI.CreateTransferTransaction(ctx).
  		TransferParams(transferParams).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TransactionsAPI.CreateTransferTransaction``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateTransferTransaction`: CreateTransferTransaction201Response
  	fmt.Fprintf(os.Stdout, "Response from `TransactionsAPI.CreateTransferTransaction`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TransactionsApi();
  const opts = {
    TransferParams: CoboWaas2.TransferParams.constructFromObject({
      request_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
      source: {
        source_type: "Asset",
        wallet_id: "d3fcfaef-f415-4210-9e5c-fbed0e090495",
      },
      token_id: "ETH_USDT",
      destination: { destination_type: "Address", account_output: { address: "19AR6YWEGbSoY8UT9Ksy9WrmrZPD5sL4Ku", amount: "1.5" } },
    }),
  };
  apiInstance.createTransferTransaction(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List asset balances
Source: https://cobo.com/developers/v2/api-references/wallets--exchange-wallet/list-asset-balances

get /wallets/{wallet_id}/exchanges/assets
This operation retrieves the asset balances in a specified Exchange Wallet. You can filter the results by trading account type or asset ID.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_asset_balances_for_exchange_wallet200_response import (
      ListAssetBalancesForExchangeWallet200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsExchangeWalletApi(api_client)
      wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      trading_account_types = "Trading,Funding"
      asset_ids = "USDT,USDC"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List asset balances
          api_response = api_instance.list_asset_balances_for_exchange_wallet(
              wallet_id,
              trading_account_types=trading_account_types,
              asset_ids=asset_ids,
              limit=limit,
              before=before,
              after=after,
          )
          print(
              "The response of WalletsExchangeWalletApi->list_asset_balances_for_exchange_wallet:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsExchangeWalletApi->list_asset_balances_for_exchange_wallet: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsExchangeWalletApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsExchangeWalletApi apiInstance = new WalletsExchangeWalletApi();
      UUID walletId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String tradingAccountTypes = "Trading,Funding";
      String assetIds = "USDT,USDC";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListAssetBalancesForExchangeWallet200Response result =
            apiInstance.listAssetBalancesForExchangeWallet(
                walletId, tradingAccountTypes, assetIds, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling WalletsExchangeWalletApi#listAssetBalancesForExchangeWallet");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	walletId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	tradingAccountTypes := "Trading,Funding"
  	assetIds := "USDT,USDC"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsExchangeWalletAPI.ListAssetBalancesForExchangeWallet(ctx, walletId).
  		TradingAccountTypes(tradingAccountTypes).
  		AssetIds(assetIds).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsExchangeWalletAPI.ListAssetBalancesForExchangeWallet``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListAssetBalancesForExchangeWallet`: ListAssetBalancesForExchangeWallet200Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `WalletsExchangeWalletAPI.ListAssetBalancesForExchangeWallet`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsExchangeWalletApi();
  const wallet_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    trading_account_types: "Trading,Funding",
    asset_ids: "USDT,USDC",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listAssetBalancesForExchangeWallet(wallet_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List supported assets
Source: https://cobo.com/developers/v2/api-references/wallets--exchange-wallet/list-supported-assets

get /wallets/exchanges/{exchange_id}/assets
This operation retrieves all the assets supported by a specified exchange.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.exchange_id import ExchangeId
  from cobo_waas2.models.list_supported_assets_for_exchange200_response import (
      ListSupportedAssetsForExchange200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsExchangeWalletApi(api_client)
      exchange_id = cobo_waas2.ExchangeId()
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List supported assets
          api_response = api_instance.list_supported_assets_for_exchange(
              exchange_id, limit=limit, before=before, after=after
          )
          print(
              "The response of WalletsExchangeWalletApi->list_supported_assets_for_exchange:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsExchangeWalletApi->list_supported_assets_for_exchange: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsExchangeWalletApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsExchangeWalletApi apiInstance = new WalletsExchangeWalletApi();
      ExchangeId exchangeId = ExchangeId.fromValue("binance");
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListSupportedAssetsForExchange200Response result =
            apiInstance.listSupportedAssetsForExchange(exchangeId, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling WalletsExchangeWalletApi#listSupportedAssetsForExchange");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	exchangeId := coboWaas2.ExchangeId("binance")
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsExchangeWalletAPI.ListSupportedAssetsForExchange(ctx, exchangeId).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsExchangeWalletAPI.ListSupportedAssetsForExchange``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListSupportedAssetsForExchange`: ListSupportedAssetsForExchange200Response
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `WalletsExchangeWalletAPI.ListSupportedAssetsForExchange`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsExchangeWalletApi();
  const exchange_id = new CoboWaas2.ExchangeId();
  const opts = {
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listSupportedAssetsForExchange(exchange_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List supported chains
Source: https://cobo.com/developers/v2/api-references/wallets--exchange-wallet/list-supported-chains

get /wallets/exchanges/{exchange_id}/assets/{asset_id}/chains
This operation retrieves all the chains supported by a specified exchange for a given asset. 

You can use this operation to confirm whether you can transfer an asset from or to your Exchange Wallet when using a specific chain.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.chain_info import ChainInfo
  from cobo_waas2.models.exchange_id import ExchangeId
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsExchangeWalletApi(api_client)
      exchange_id = cobo_waas2.ExchangeId()
      asset_id = "USDT"

      try:
          # List supported chains
          api_response = api_instance.list_supported_chains_for_exchange(
              exchange_id, asset_id
          )
          print(
              "The response of WalletsExchangeWalletApi->list_supported_chains_for_exchange:\n"
          )
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsExchangeWalletApi->list_supported_chains_for_exchange: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsExchangeWalletApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsExchangeWalletApi apiInstance = new WalletsExchangeWalletApi();
      ExchangeId exchangeId = ExchangeId.fromValue("binance");
      String assetId = "USDT";
      try {
        List<ChainInfo> result = apiInstance.listSupportedChainsForExchange(exchangeId, assetId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println(
            "Exception when calling WalletsExchangeWalletApi#listSupportedChainsForExchange");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	exchangeId := coboWaas2.ExchangeId("binance")
  	assetId := "USDT"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsExchangeWalletAPI.ListSupportedChainsForExchange(ctx, exchangeId, assetId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsExchangeWalletAPI.ListSupportedChainsForExchange``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListSupportedChainsForExchange`: []ChainInfo
  	fmt.Fprintf(
  		os.Stdout,
  		"Response from `WalletsExchangeWalletAPI.ListSupportedChainsForExchange`: %v\n",
  		resp,
  	)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsExchangeWalletApi();
  const exchange_id = new CoboWaas2.ExchangeId();
  const asset_id = "USDT";
  apiInstance.listSupportedChainsForExchange(exchange_id, asset_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List supported exchanges
Source: https://cobo.com/developers/v2/api-references/wallets--exchange-wallet/list-supported-exchanges

get /wallets/exchanges
This operation retrieves the information about the exchanges supported by Cobo's Exchange Wallets, including exchange IDs and trading account types.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_exchanges200_response_inner import (
      ListExchanges200ResponseInner,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsExchangeWalletApi(api_client)

      try:
          # List supported exchanges
          api_response = api_instance.list_exchanges()
          print("The response of WalletsExchangeWalletApi->list_exchanges:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsExchangeWalletApi->list_exchanges: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsExchangeWalletApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsExchangeWalletApi apiInstance = new WalletsExchangeWalletApi();
      try {
        List<ListExchanges200ResponseInner> result = apiInstance.listExchanges();
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsExchangeWalletApi#listExchanges");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsExchangeWalletAPI.ListExchanges(ctx).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsExchangeWalletAPI.ListExchanges``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListExchanges`: []ListExchanges200ResponseInner
  	fmt.Fprintf(os.Stdout, "Response from `WalletsExchangeWalletAPI.ListExchanges`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsExchangeWalletApi();
  apiInstance.listExchanges().then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Cancel TSS request
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/cancel-tss-request

post /wallets/mpc/vaults/{vault_id}/tss_requests/{tss_request_id}/cancel
This operation cancels a TSS request.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tss_request import TSSRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      tss_request_id = "20240711114129000132315000003970"

      try:
          # Cancel TSS request
          api_response = api_instance.cancel_tss_request_by_id(vault_id, tss_request_id)
          print("The response of WalletsMPCWalletsApi->cancel_tss_request_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->cancel_tss_request_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String tssRequestId = "20240711114129000132315000003970";
      try {
        TSSRequest result = apiInstance.cancelTssRequestById(vaultId, tssRequestId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#cancelTssRequestById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	tssRequestId := "20240711114129000132315000003970"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.CancelTssRequestById(ctx, vaultId, tssRequestId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.CancelTssRequestById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CancelTssRequestById`: TSSRequest
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.CancelTssRequestById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const tss_request_id = "20240711114129000132315000003970";
  apiInstance.cancelTssRequestById(vault_id, tss_request_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get TSS request
Source: https://cobo.com/developers/v2/api-references/wallets--mpc-wallets/get-tss-request

get /wallets/mpc/vaults/{vault_id}/tss_requests/{tss_request_id}
This operation retrieves detailed information about a TSS request.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.tss_request import TSSRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.WalletsMPCWalletsApi(api_client)
      vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      tss_request_id = "20240711114129000132315000003970"

      try:
          # Get TSS request
          api_response = api_instance.get_tss_request_by_id(vault_id, tss_request_id)
          print("The response of WalletsMPCWalletsApi->get_tss_request_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling WalletsMPCWalletsApi->get_tss_request_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.WalletsMpcWalletsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      WalletsMpcWalletsApi apiInstance = new WalletsMpcWalletsApi();
      UUID vaultId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      String tssRequestId = "20240711114129000132315000003970";
      try {
        TSSRequest result = apiInstance.getTssRequestById(vaultId, tssRequestId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling WalletsMpcWalletsApi#getTssRequestById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	vaultId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	tssRequestId := "20240711114129000132315000003970"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.WalletsMPCWalletsAPI.GetTssRequestById(ctx, vaultId, tssRequestId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `WalletsMPCWalletsAPI.GetTssRequestById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetTssRequestById`: TSSRequest
  	fmt.Fprintf(os.Stdout, "Response from `WalletsMPCWalletsAPI.GetTssRequestById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.WalletsMPCWalletsApi();
  const vault_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const tss_request_id = "20240711114129000132315000003970";
  apiInstance.getTssRequestById(vault_id, tss_request_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get approval request details
Source: https://cobo.com/developers/v2/api-references/appworkflows/get-approval-request-details

get /app/workflows/approval_requests/{approval_id}
This operation retrieves the details of a specific approval request.

<Note>To use the approval workflow operations, you must use the Cobo OAuth authentication method ([Org Access Token](https://www.cobo.com/developers/v2/apps/org-access-tokens)).</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.approval_request_detail import ApprovalRequestDetail
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AppWorkflowsApi(api_client)
      approval_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Get approval request details
          api_response = api_instance.get_approval_request_by_id(approval_id)
          print("The response of AppWorkflowsApi->get_approval_request_by_id:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling AppWorkflowsApi->get_approval_request_by_id: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AppWorkflowsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AppWorkflowsApi apiInstance = new AppWorkflowsApi();
      UUID approvalId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      try {
        ApprovalRequestDetail result = apiInstance.getApprovalRequestById(approvalId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AppWorkflowsApi#getApprovalRequestById");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	approvalId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AppWorkflowsAPI.GetApprovalRequestById(ctx, approvalId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `AppWorkflowsAPI.GetApprovalRequestById``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetApprovalRequestById`: ApprovalRequestDetail
  	fmt.Fprintf(os.Stdout, "Response from `AppWorkflowsAPI.GetApprovalRequestById`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AppWorkflowsApi();
  const approval_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.getApprovalRequestById(approval_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List app workflows
Source: https://cobo.com/developers/v2/api-references/appworkflows/list-app-workflows

get /app/workflows
This operation retrieves all approval workflows of an Cobo Portal App.
<Note>You need to [configure approval workflow](https://www.cobo.com/developers/v2/apps/configure-workflow) in the app Manifest file first.</Note>
<Note>To use the approval workflow operations, you must use the Cobo OAuth authentication method ([Org Access Token](https://www.cobo.com/developers/v2/apps/org-access-tokens)).</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.app_workflow import AppWorkflow
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AppWorkflowsApi(api_client)

      try:
          # List app workflows
          api_response = api_instance.list_app_workflows()
          print("The response of AppWorkflowsApi->list_app_workflows:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling AppWorkflowsApi->list_app_workflows: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AppWorkflowsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AppWorkflowsApi apiInstance = new AppWorkflowsApi();
      try {
        List<AppWorkflow> result = apiInstance.listAppWorkflows();
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AppWorkflowsApi#listAppWorkflows");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AppWorkflowsAPI.ListAppWorkflows(ctx).Execute()
  	if err != nil {
  		fmt.Fprintf(os.Stderr, "Error when calling `AppWorkflowsAPI.ListAppWorkflows``: %v\n", err)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListAppWorkflows`: []AppWorkflow
  	fmt.Fprintf(os.Stdout, "Response from `AppWorkflowsAPI.ListAppWorkflows`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AppWorkflowsApi();
  apiInstance.listAppWorkflows().then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List approval requests
Source: https://cobo.com/developers/v2/api-references/appworkflows/list-approval-requests

get /app/workflows/approval_requests
This operation retrieves a list of approval requests.

<Note>To use the approval workflow operations, you must use the Cobo OAuth authentication method ([Org Access Token](https://www.cobo.com/developers/v2/apps/org-access-tokens)).</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_approval_requests200_response import (
      ListApprovalRequests200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AppWorkflowsApi(api_client)
      operation_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List approval requests
          api_response = api_instance.list_approval_requests(
              operation_id, limit=limit, before=before, after=after
          )
          print("The response of AppWorkflowsApi->list_approval_requests:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling AppWorkflowsApi->list_approval_requests: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AppWorkflowsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AppWorkflowsApi apiInstance = new AppWorkflowsApi();
      String operationId = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListApprovalRequests200Response result =
            apiInstance.listApprovalRequests(operationId, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AppWorkflowsApi#listApprovalRequests");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	operationId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AppWorkflowsAPI.ListApprovalRequests(ctx).
  		OperationId(operationId).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `AppWorkflowsAPI.ListApprovalRequests``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListApprovalRequests`: ListApprovalRequests200Response
  	fmt.Fprintf(os.Stdout, "Response from `AppWorkflowsAPI.ListApprovalRequests`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AppWorkflowsApi();
  const operation_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listApprovalRequests(operation_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Request workflow approval
Source: https://cobo.com/developers/v2/api-references/appworkflows/request-workflow-approval

post /app/workflows/approval_requests
This operation triggers a specified workflow and generates a new approval request.

<Note>To use the approval workflow operations, you must use the Cobo OAuth authentication method ([Org Access Token](https://www.cobo.com/developers/v2/apps/org-access-tokens)).</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_approval_request201_response import (
      CreateApprovalRequest201Response,
  )
  from cobo_waas2.models.request_approval import RequestApproval
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AppWorkflowsApi(api_client)
      request_approval = cobo_waas2.RequestApproval(
          operation_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
          request_id="f47ac10b-58cc-4372-a567-0e02b2c3d479",
          initiator_email="johnsmith@example.com",
          fields=[
              cobo_waas2.AppWorkflowField(field="amount", value_type="INT", value="11.23")
          ],
          guard_template="example_string",
      )

      try:
          # Request workflow approval
          api_response = api_instance.create_approval_request(
              request_approval=request_approval
          )
          print("The response of AppWorkflowsApi->create_approval_request:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling AppWorkflowsApi->create_approval_request: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AppWorkflowsApi;
  import com.cobo.waas2.model.*;
  import java.util.Arrays;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AppWorkflowsApi apiInstance = new AppWorkflowsApi();
      RequestApproval requestApproval =
          new RequestApproval()
              .operationId("f47ac10b-58cc-4372-a567-0e02b2c3d479")
              .requestId("f47ac10b-58cc-4372-a567-0e02b2c3d479")
              .initiatorEmail("johnsmith@example.com")
              .fields(
                  Arrays.asList(
                      new AppWorkflowField()
                          .field("amount")
                          .valueType(PolicyFieldValueType.INT)
                          .value("11.23")))
              .guardTemplate("example_string");
      try {
        CreateApprovalRequest201Response result = apiInstance.createApprovalRequest(requestApproval);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AppWorkflowsApi#createApprovalRequest");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	requestApproval := *coboWaas2.NewRequestApproval("f47ac10b-58cc-4372-a567-0e02b2c3d479", "f47ac10b-58cc-4372-a567-0e02b2c3d479", "johnsmith@example.com", []coboWaas2.AppWorkflowField{*coboWaas2.NewAppWorkflowField("amount", coboWaas2.PolicyFieldValueType("INT"), "11.23")}, "GuardTemplate_example")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AppWorkflowsAPI.CreateApprovalRequest(ctx).
  		RequestApproval(requestApproval).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `AppWorkflowsAPI.CreateApprovalRequest``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateApprovalRequest`: CreateApprovalRequest201Response
  	fmt.Fprintf(os.Stdout, "Response from `AppWorkflowsAPI.CreateApprovalRequest`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AppWorkflowsApi();
  const opts = {
    RequestApproval: CoboWaas2.RequestApproval.constructFromObject({
      operation_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
      request_id: "f47ac10b-58cc-4372-a567-0e02b2c3d479",
      initiator_email: "johnsmith@example.com",
      fields: [{ field: "amount", value_type: "INT", value: "11.23" }],
      guard_template: "example_string",
    }),
  };
  apiInstance.createApprovalRequest(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Revoke approval request
Source: https://cobo.com/developers/v2/api-references/appworkflows/revoke-approval-request

post /app/workflows/approval_requests/{approval_id}/revoke
This operation revokes a pending approval request.

<Note>To use the approval workflow operations, you must use the Cobo OAuth authentication method ([Org Access Token](https://www.cobo.com/developers/v2/apps/org-access-tokens)).</Note>


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.revoke_approval_request201_response import (
      RevokeApprovalRequest201Response,
  )
  from cobo_waas2.models.revoke_approval_request_request import (
      RevokeApprovalRequestRequest,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.AppWorkflowsApi(api_client)
      approval_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"
      revoke_approval_request_request = cobo_waas2.RevokeApprovalRequestRequest(
          initiator_email="johnsmith@example.com"
      )

      try:
          # Revoke approval request
          api_response = api_instance.revoke_approval_request(
              approval_id, revoke_approval_request_request=revoke_approval_request_request
          )
          print("The response of AppWorkflowsApi->revoke_approval_request:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling AppWorkflowsApi->revoke_approval_request: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.AppWorkflowsApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      AppWorkflowsApi apiInstance = new AppWorkflowsApi();
      UUID approvalId = UUID.fromString("f47ac10b-58cc-4372-a567-0e02b2c3d479");
      RevokeApprovalRequestRequest revokeApprovalRequestRequest =
          new RevokeApprovalRequestRequest().initiatorEmail("johnsmith@example.com");
      try {
        RevokeApprovalRequest201Response result =
            apiInstance.revokeApprovalRequest(approvalId, revokeApprovalRequestRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling AppWorkflowsApi#revokeApprovalRequest");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	approvalId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"
  	revokeApprovalRequestRequest := *coboWaas2.NewRevokeApprovalRequestRequest("johnsmith@example.com")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.AppWorkflowsAPI.RevokeApprovalRequest(ctx, approvalId).
  		RevokeApprovalRequestRequest(revokeApprovalRequestRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `AppWorkflowsAPI.RevokeApprovalRequest``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `RevokeApprovalRequest`: RevokeApprovalRequest201Response
  	fmt.Fprintf(os.Stdout, "Response from `AppWorkflowsAPI.RevokeApprovalRequest`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.AppWorkflowsApi();
  const approval_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  const opts = {
    RevokeApprovalRequestRequest:
      CoboWaas2.RevokeApprovalRequestRequest.constructFromObject({
        initiator_email: "johnsmith@example.com",
      }),
  };
  apiInstance.revokeApprovalRequest(approval_id, opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Retry callback message
Source: https://cobo.com/developers/v2/api-references/developers/retry-callback-message

post /developers/callback_messages/{message_id}/retry
This operation resends a callback message that failed previously.

If your callback endpoint doesn't respond as expected, the WaaS service will retry sending the callback message up to 30 times. After that, the callback message status will be `Failed`. Use this operation to resend the message. For more details, refer to [Webhooks and Callbacks](https://www.cobo.com/developers/v2/guides/webhooks-callbacks/set-up-endpoint#callback-messages).


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.retry_callback_message201_response import (
      RetryCallbackMessage201Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.DevelopersApi(api_client)
      message_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479"

      try:
          # Retry callback message
          api_response = api_instance.retry_callback_message(message_id)
          print("The response of DevelopersApi->retry_callback_message:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling DevelopersApi->retry_callback_message: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.DevelopersApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      DevelopersApi apiInstance = new DevelopersApi();
      String messageId = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
      try {
        RetryCallbackMessage201Response result = apiInstance.retryCallbackMessage(messageId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling DevelopersApi#retryCallbackMessage");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	messageId := "f47ac10b-58cc-4372-a567-0e02b2c3d479"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.DevelopersAPI.RetryCallbackMessage(ctx, messageId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `DevelopersAPI.RetryCallbackMessage``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `RetryCallbackMessage`: RetryCallbackMessage201Response
  	fmt.Fprintf(os.Stdout, "Response from `DevelopersAPI.RetryCallbackMessage`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.DevelopersApi();
  const message_id = "f47ac10b-58cc-4372-a567-0e02b2c3d479";
  apiInstance.retryCallbackMessage(message_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Cancel Satoshi Test challenge
Source: https://cobo.com/developers/v2/api-references/travelrule/cancel-satoshi-test-challenge

post /travel_rule/satoshi_test/challenge/cancel
This operation cancels a Satoshi Test challenge that is currently in `PREPARE` or `PENDING` status. Typical use case: the counterparty decides to switch verification methods before transferring.

Once cancelled, the challenge status becomes `DELETED` and the on-chain match will no longer be observed. Challenges already in `MATCHED`, `VERIFIED`, `EXPIRED`, or `DELETED` state cannot be cancelled.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.cancel_satoshi_test_challenge_request import (
      CancelSatoshiTestChallengeRequest,
  )
  from cobo_waas2.models.satoshi_test_cancel_result import SatoshiTestCancelResult
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TravelRuleApi(api_client)
      cancel_satoshi_test_challenge_request = (
          cobo_waas2.CancelSatoshiTestChallengeRequest()
      )

      try:
          # Cancel Satoshi Test challenge
          api_response = api_instance.cancel_satoshi_test_challenge(
              cancel_satoshi_test_challenge_request=cancel_satoshi_test_challenge_request
          )
          print("The response of TravelRuleApi->cancel_satoshi_test_challenge:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TravelRuleApi->cancel_satoshi_test_challenge: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TravelRuleApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TravelRuleApi apiInstance = new TravelRuleApi();
      CancelSatoshiTestChallengeRequest cancelSatoshiTestChallengeRequest =
          new CancelSatoshiTestChallengeRequest();
      try {
        SatoshiTestCancelResult result =
            apiInstance.cancelSatoshiTestChallenge(cancelSatoshiTestChallengeRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TravelRuleApi#cancelSatoshiTestChallenge");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	cancelSatoshiTestChallengeRequest := *coboWaas2.NewCancelSatoshiTestChallengeRequest("a1b2c3d4-e5f6-7890-abcd-ef1234567890")

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TravelRuleAPI.CancelSatoshiTestChallenge(ctx).
  		CancelSatoshiTestChallengeRequest(cancelSatoshiTestChallengeRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TravelRuleAPI.CancelSatoshiTestChallenge``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CancelSatoshiTestChallenge`: SatoshiTestCancelResult
  	fmt.Fprintf(os.Stdout, "Response from `TravelRuleAPI.CancelSatoshiTestChallenge`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TravelRuleApi();
  const opts = {
    CancelSatoshiTestChallengeRequest:
      new CoboWaas2.CancelSatoshiTestChallengeRequest(),
  };
  apiInstance.cancelSatoshiTestChallenge(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Create Satoshi Test challenge
Source: https://cobo.com/developers/v2/api-references/travelrule/create-satoshi-test-challenge

post /travel_rule/satoshi_test/challenge
This operation creates a Satoshi Test challenge for self-custody address verification. Satoshi Test verifies address ownership by having the counterparty transfer a small, uniquely-generated amount from their wallet to a Cobo-controlled verification address.

A single endpoint covers both flows via the `action` parameter:
- **Two-step flow** (`action=PREPARE` then `action=SUBMIT`): Preview the verification details first, then activate. The 180-minute countdown only starts on `SUBMIT`. The server uses `(chain_id, from_address)` as the idempotency key, so the second call automatically targets the prepared challenge. For extra safety, pass the `challenge_id` returned by `PREPARE` in the subsequent `SUBMIT` call — it pins the activation to that specific challenge.
- **One-shot flow** (`action=SUBMIT` directly, without `challenge_id`): Prepare and submit in a single call. The challenge is created directly in `PENDING` state with the countdown started.

If the counterparty address has already been verified, the operation returns HTTP 400 `ADDRESS_ALREADY_VERIFIED`. Call [List address verifications](#operation/list_address_verifications) with `chain_id`, `address`, and `status=VERIFIED` first to pre-check.

Supported chains: `BTC`, `ETH`, `BASE_ETH`, `BSC_BNB`, `TRON`.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.create_satoshi_test_challenge_request import (
      CreateSatoshiTestChallengeRequest,
  )
  from cobo_waas2.models.satoshi_test_challenge import SatoshiTestChallenge
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TravelRuleApi(api_client)
      create_satoshi_test_challenge_request = (
          cobo_waas2.CreateSatoshiTestChallengeRequest()
      )

      try:
          # Create Satoshi Test challenge
          api_response = api_instance.create_satoshi_test_challenge(
              create_satoshi_test_challenge_request=create_satoshi_test_challenge_request
          )
          print("The response of TravelRuleApi->create_satoshi_test_challenge:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TravelRuleApi->create_satoshi_test_challenge: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TravelRuleApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TravelRuleApi apiInstance = new TravelRuleApi();
      CreateSatoshiTestChallengeRequest createSatoshiTestChallengeRequest =
          new CreateSatoshiTestChallengeRequest();
      try {
        SatoshiTestChallenge result =
            apiInstance.createSatoshiTestChallenge(createSatoshiTestChallengeRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TravelRuleApi#createSatoshiTestChallenge");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	createSatoshiTestChallengeRequest := *coboWaas2.NewCreateSatoshiTestChallengeRequest(coboWaas2.SatoshiTestChallengeAction("PREPARE"), "ETH", "0x1234567890abcdef1234567890abcdef12345678", "123e4567-e89b-12d3-a456-426614174000", coboWaas2.TravelRuleTransactionType("DEPOSIT"))

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TravelRuleAPI.CreateSatoshiTestChallenge(ctx).
  		CreateSatoshiTestChallengeRequest(createSatoshiTestChallengeRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TravelRuleAPI.CreateSatoshiTestChallenge``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `CreateSatoshiTestChallenge`: SatoshiTestChallenge
  	fmt.Fprintf(os.Stdout, "Response from `TravelRuleAPI.CreateSatoshiTestChallenge`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TravelRuleApi();
  const opts = {
    CreateSatoshiTestChallengeRequest:
      new CoboWaas2.CreateSatoshiTestChallengeRequest(),
  };
  apiInstance.createSatoshiTestChallenge(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get address verification
Source: https://cobo.com/developers/v2/api-references/travelrule/get-address-verification

get /travel_rule/address_verifications/{verification_id}
Retrieve a single self-custody address verification record by its `verification_id`, including method-specific provenance:

- `verification_method=SIGNATURE` → `signature_detail` is populated.
- `verification_method=SATOSHI_TEST` → `satoshi_test_detail` carries the latest challenge state (`status`, `remaining_seconds`, `matched_txid`).

Use [List address verifications](#operation/list_address_verifications) to discover `verification_id` values.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.address_verification_detail import AddressVerificationDetail
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TravelRuleApi(api_client)
      verification_id = "fb377ea5-a97a-49b4-955d-23f8fdd5177a"

      try:
          # Get address verification
          api_response = api_instance.get_address_verification(verification_id)
          print("The response of TravelRuleApi->get_address_verification:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TravelRuleApi->get_address_verification: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TravelRuleApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TravelRuleApi apiInstance = new TravelRuleApi();
      UUID verificationId = UUID.fromString("fb377ea5-a97a-49b4-955d-23f8fdd5177a");
      try {
        AddressVerificationDetail result = apiInstance.getAddressVerification(verificationId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TravelRuleApi#getAddressVerification");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	verificationId := "fb377ea5-a97a-49b4-955d-23f8fdd5177a"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TravelRuleAPI.GetAddressVerification(ctx, verificationId).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TravelRuleAPI.GetAddressVerification``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetAddressVerification`: AddressVerificationDetail
  	fmt.Fprintf(os.Stdout, "Response from `TravelRuleAPI.GetAddressVerification`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TravelRuleApi();
  const verification_id = "fb377ea5-a97a-49b4-955d-23f8fdd5177a";
  apiInstance.getAddressVerification(verification_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get Satoshi Test challenge
Source: https://cobo.com/developers/v2/api-references/travelrule/get-satoshi-test-challenge

get /travel_rule/satoshi_test/challenge/status
This operation returns the current state of a Satoshi Test challenge — useful for polling after submission. The response contains the challenge `status` and `remaining_seconds`.

Recommended polling interval: 10–30 seconds. The challenge will transition through `PENDING` → `MATCHED` → `VERIFIED` once the counterparty's transfer is observed and confirmed on chain. If the challenge is not matched within 180 minutes, the status becomes `EXPIRED`.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.satoshi_test_challenge import SatoshiTestChallenge
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TravelRuleApi(api_client)
      challenge_id = "a1b2c3d4-e5f6-7890-abcd-ef1234567890"

      try:
          # Get Satoshi Test challenge
          api_response = api_instance.get_satoshi_test_challenge(challenge_id)
          print("The response of TravelRuleApi->get_satoshi_test_challenge:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TravelRuleApi->get_satoshi_test_challenge: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TravelRuleApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TravelRuleApi apiInstance = new TravelRuleApi();
      UUID challengeId = UUID.fromString("a1b2c3d4-e5f6-7890-abcd-ef1234567890");
      try {
        SatoshiTestChallenge result = apiInstance.getSatoshiTestChallenge(challengeId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TravelRuleApi#getSatoshiTestChallenge");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	challengeId := "a1b2c3d4-e5f6-7890-abcd-ef1234567890"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TravelRuleAPI.GetSatoshiTestChallenge(ctx).
  		ChallengeId(challengeId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TravelRuleAPI.GetSatoshiTestChallenge``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetSatoshiTestChallenge`: SatoshiTestChallenge
  	fmt.Fprintf(os.Stdout, "Response from `TravelRuleAPI.GetSatoshiTestChallenge`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TravelRuleApi();
  const challenge_id = "a1b2c3d4-e5f6-7890-abcd-ef1234567890";
  apiInstance.getSatoshiTestChallenge(challenge_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Get self-custody signature challenge
Source: https://cobo.com/developers/v2/api-references/travelrule/get-self-custody-signature-challenge

get /travel_rule/signature_challenge
This operation issues a one-time, time-bounded message for a self-custody wallet address to sign, in order to prove wallet ownership. The signature is then submitted via [Submit Travel Rule information for deposits](#operation/submit_deposit_travel_rule_info) or [withdrawals](#operation/submit_withdraw_travel_rule_info).

Use this endpoint when you want to verify the counterparty's self-custody address via off-chain signature. For address verification via on-chain micro-deposit, use the Satoshi Test endpoints (`/travel_rule/satoshi_test/...`) instead.

The challenge is valid for a short window (returned as `expires_in`, currently 30 seconds). Calling this endpoint again for the same transaction rotates the challenge — only the latest issued value will verify.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.signature_challenge import SignatureChallenge
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TravelRuleApi(api_client)
      transaction_type = "DEPOSIT"
      transaction_id = "123e4567-e89b-12d3-a456-426614174000"

      try:
          # Get self-custody signature challenge
          api_response = api_instance.get_signature_challenge(
              transaction_type, transaction_id
          )
          print("The response of TravelRuleApi->get_signature_challenge:\n")
          pprint(api_response)
      except Exception as e:
          print("Exception when calling TravelRuleApi->get_signature_challenge: %s\n" % e)

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TravelRuleApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TravelRuleApi apiInstance = new TravelRuleApi();
      String transactionType = "DEPOSIT";
      UUID transactionId = UUID.fromString("123e4567-e89b-12d3-a456-426614174000");
      try {
        SignatureChallenge result = apiInstance.getSignatureChallenge(transactionType, transactionId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TravelRuleApi#getSignatureChallenge");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionType := "DEPOSIT"
  	transactionId := "123e4567-e89b-12d3-a456-426614174000"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TravelRuleAPI.GetSignatureChallenge(ctx).
  		TransactionType(transactionType).
  		TransactionId(transactionId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TravelRuleAPI.GetSignatureChallenge``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetSignatureChallenge`: SignatureChallenge
  	fmt.Fprintf(os.Stdout, "Response from `TravelRuleAPI.GetSignatureChallenge`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TravelRuleApi();
  const transaction_type = "DEPOSIT";
  const transaction_id = "123e4567-e89b-12d3-a456-426614174000";
  apiInstance.getSignatureChallenge(transaction_type, transaction_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List address verifications
Source: https://cobo.com/developers/v2/api-references/travelrule/list-address-verifications

get /travel_rule/address_verifications
List self-custody address verification records under the current organization with optional filters and cursor-based pagination.

Records are sorted by creation time descending (most recent first). Use `limit` plus `before` / `after` cursors from the previous page's `pagination` block to traverse pages.

Each record's `status` is one of `PENDING`, `VERIFIED`, or `FAILED`.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.address_verification_status import AddressVerificationStatus
  from cobo_waas2.models.list_address_verifications200_response import (
      ListAddressVerifications200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TravelRuleApi(api_client)
      status = cobo_waas2.AddressVerificationStatus()
      chain_id = "ETH"
      address = "0x1234567890abcdef1234567890abcdef12345678"
      limit = 10
      before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
      after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

      try:
          # List address verifications
          api_response = api_instance.list_address_verifications(
              status=status,
              chain_id=chain_id,
              address=address,
              limit=limit,
              before=before,
              after=after,
          )
          print("The response of TravelRuleApi->list_address_verifications:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TravelRuleApi->list_address_verifications: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TravelRuleApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TravelRuleApi apiInstance = new TravelRuleApi();
      AddressVerificationStatus status = AddressVerificationStatus.fromValue("PENDING");
      String chainId = "ETH";
      String address = "0x1234567890abcdef1234567890abcdef12345678";
      Integer limit = 10;
      String before = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1";
      String after = "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk";
      try {
        ListAddressVerifications200Response result =
            apiInstance.listAddressVerifications(status, chainId, address, limit, before, after);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TravelRuleApi#listAddressVerifications");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	status := coboWaas2.AddressVerificationStatus("PENDING")
  	chainId := "ETH"
  	address := "0x1234567890abcdef1234567890abcdef12345678"
  	limit := int32(10)
  	before := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1"
  	after := "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TravelRuleAPI.ListAddressVerifications(ctx).
  		Status(status).
  		ChainId(chainId).
  		Address(address).
  		Limit(limit).
  		Before(before).
  		After(after).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TravelRuleAPI.ListAddressVerifications``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListAddressVerifications`: ListAddressVerifications200Response
  	fmt.Fprintf(os.Stdout, "Response from `TravelRuleAPI.ListAddressVerifications`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TravelRuleApi();
  const opts = {
    status: new CoboWaas2.AddressVerificationStatus(),
    chain_id: "ETH",
    address: "0x1234567890abcdef1234567890abcdef12345678",
    limit: 10,
    before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1",
    after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",
  };
  apiInstance.listAddressVerifications(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# List supported countries
Source: https://cobo.com/developers/v2/api-references/travelrule/list-supported-countries

get /travel_rule/transaction/countries
This operation retrieves a list of supported countries that can be used when submitting Travel Rule information.

Use this endpoint to obtain valid country values for:
  - Place of incorporation of a legal entity
  - Place of birth of a natural person


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.list_supported_countries200_response_inner import (
      ListSupportedCountries200ResponseInner,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TravelRuleApi(api_client)

      try:
          # List supported countries
          api_response = api_instance.list_supported_countries()
          print("The response of TravelRuleApi->list_supported_countries:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TravelRuleApi->list_supported_countries: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TravelRuleApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TravelRuleApi apiInstance = new TravelRuleApi();
      try {
        List<ListSupportedCountries200ResponseInner> result = apiInstance.listSupportedCountries();
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TravelRuleApi#listSupportedCountries");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TravelRuleAPI.ListSupportedCountries(ctx).Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TravelRuleAPI.ListSupportedCountries``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `ListSupportedCountries`: []ListSupportedCountries200ResponseInner
  	fmt.Fprintf(os.Stdout, "Response from `TravelRuleAPI.ListSupportedCountries`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TravelRuleApi();
  apiInstance.listSupportedCountries().then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Retrieve transaction limitations
Source: https://cobo.com/developers/v2/api-references/travelrule/retrieve-transaction-limitations

get /travel_rule/transaction/limitation
<Note>The `self_custody_wallet_challenge` field in the response is deprecated. To obtain a signature challenge, call [Get self-custody signature challenge](#operation/get_signature_challenge) instead. This operation itself is not deprecated and continues to return the VASP list, threshold info, connect wallet list, and Satoshi Test support.</Note>

This operation retrieves Travel Rule requirements and available options for a transaction based on its transaction type and ID.

Use this endpoint before submitting Travel Rule information to understand the requirements and available options for your transaction.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.get_transaction_limitation200_response import (
      GetTransactionLimitation200Response,
  )
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TravelRuleApi(api_client)
      transaction_type = "DEPOSIT"
      transaction_id = "123e4567-e89b-12d3-a456-426614174000"

      try:
          # Retrieve transaction limitations
          api_response = api_instance.get_transaction_limitation(
              transaction_type, transaction_id
          )
          print("The response of TravelRuleApi->get_transaction_limitation:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TravelRuleApi->get_transaction_limitation: %s\n" % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TravelRuleApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TravelRuleApi apiInstance = new TravelRuleApi();
      String transactionType = "DEPOSIT";
      UUID transactionId = UUID.fromString("123e4567-e89b-12d3-a456-426614174000");
      try {
        GetTransactionLimitation200Response result =
            apiInstance.getTransactionLimitation(transactionType, transactionId);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TravelRuleApi#getTransactionLimitation");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	transactionType := "DEPOSIT"
  	transactionId := "123e4567-e89b-12d3-a456-426614174000"

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TravelRuleAPI.GetTransactionLimitation(ctx).
  		TransactionType(transactionType).
  		TransactionId(transactionId).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TravelRuleAPI.GetTransactionLimitation``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `GetTransactionLimitation`: GetTransactionLimitation200Response
  	fmt.Fprintf(os.Stdout, "Response from `TravelRuleAPI.GetTransactionLimitation`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TravelRuleApi();
  const transaction_type = "DEPOSIT";
  const transaction_id = "123e4567-e89b-12d3-a456-426614174000";
  apiInstance.getTransactionLimitation(transaction_type, transaction_id).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Submit Travel Rule information for deposits
Source: https://cobo.com/developers/v2/api-references/travelrule/submit-travel-rule-information-for-deposits

post /travel_rule/transaction/deposit/travel_rule_info
This operation submits Travel Rule information for a deposit transaction.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.submit_deposit_travel_rule_info201_response import (
      SubmitDepositTravelRuleInfo201Response,
  )
  from cobo_waas2.models.travel_rule_deposit_request import TravelRuleDepositRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TravelRuleApi(api_client)
      travel_rule_deposit_request = cobo_waas2.TravelRuleDepositRequest()

      try:
          # Submit Travel Rule information for deposits
          api_response = api_instance.submit_deposit_travel_rule_info(
              travel_rule_deposit_request=travel_rule_deposit_request
          )
          print("The response of TravelRuleApi->submit_deposit_travel_rule_info:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TravelRuleApi->submit_deposit_travel_rule_info: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TravelRuleApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TravelRuleApi apiInstance = new TravelRuleApi();
      TravelRuleDepositRequest travelRuleDepositRequest = new TravelRuleDepositRequest();
      try {
        SubmitDepositTravelRuleInfo201Response result =
            apiInstance.submitDepositTravelRuleInfo(travelRuleDepositRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TravelRuleApi#submitDepositTravelRuleInfo");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	travelRuleDepositRequest := *coboWaas2.NewTravelRuleDepositRequest("f47ac10b-58cc-4372-a567-0e02b2c3d479", coboWaas2.TravelRuleDepositRequest_travel_rule_info{SelfCustodyWallet: coboWaas2.NewSelfCustodyWallet(coboWaas2.DestinationWalletType("EXCHANGES_OR_VASP"), "challenge_token_abc123", "0x1234567890abcdef1234567890abcdef12345678", "0xf0a0ca69dd3afc57235c72aba3ff1f1144ee5409aeec013a9b17cdb58d0185a66a525945bfbd66e87bf0503eb0b83bf90cb973a8cbb730d19dc032e00dfe393a1c")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TravelRuleAPI.SubmitDepositTravelRuleInfo(ctx).
  		TravelRuleDepositRequest(travelRuleDepositRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TravelRuleAPI.SubmitDepositTravelRuleInfo``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `SubmitDepositTravelRuleInfo`: SubmitDepositTravelRuleInfo201Response
  	fmt.Fprintf(os.Stdout, "Response from `TravelRuleAPI.SubmitDepositTravelRuleInfo`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TravelRuleApi();
  const opts = {
    TravelRuleDepositRequest: new CoboWaas2.TravelRuleDepositRequest(),
  };
  apiInstance.submitDepositTravelRuleInfo(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Submit Travel Rule information for withdrawals
Source: https://cobo.com/developers/v2/api-references/travelrule/submit-travel-rule-information-for-withdrawals

post /travel_rule/transaction/withdraw/travel_rule_info
This operation submits Travel Rule information for a withdrawal transaction.


<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<RequestExample>
  ```python Python theme={null}
  import cobo_waas2
  from cobo_waas2.models.submit_deposit_travel_rule_info201_response import (
      SubmitDepositTravelRuleInfo201Response,
  )
  from cobo_waas2.models.travel_rule_withdraw_request import TravelRuleWithdrawRequest
  from cobo_waas2.rest import ApiException
  from pprint import pprint

  # See configuration.py for a list of all supported configurations.
  configuration = cobo_waas2.Configuration(
      # Replace `<YOUR_PRIVATE_KEY>` with your private key
      api_private_key="<YOUR_PRIVATE_KEY>",
      # Select the development environment. To use the production environment, change the URL to https://api.cobo.com/v2.
      host="https://api.dev.cobo.com/v2",
  )
  # Enter a context with an instance of the API client
  with cobo_waas2.ApiClient(configuration) as api_client:
      # Create an instance of the API class
      api_instance = cobo_waas2.TravelRuleApi(api_client)
      travel_rule_withdraw_request = cobo_waas2.TravelRuleWithdrawRequest()

      try:
          # Submit Travel Rule information for withdrawals
          api_response = api_instance.submit_withdraw_travel_rule_info(
              travel_rule_withdraw_request=travel_rule_withdraw_request
          )
          print("The response of TravelRuleApi->submit_withdraw_travel_rule_info:\n")
          pprint(api_response)
      except Exception as e:
          print(
              "Exception when calling TravelRuleApi->submit_withdraw_travel_rule_info: %s\n"
              % e
          )

  ```

  ```java Java theme={null}
  // Import classes:
  import com.cobo.waas2.ApiClient;
  import com.cobo.waas2.ApiException;
  import com.cobo.waas2.Configuration;
  import com.cobo.waas2.Env;
  import com.cobo.waas2.api.TravelRuleApi;
  import com.cobo.waas2.model.*;

  public class Example {
    public static void main(String[] args) {
      ApiClient defaultClient = Configuration.getDefaultApiClient();
      // Select the development environment. To use the production environment, replace `Env.DEV` with
      // `Env.PROD
      defaultClient.setEnv(Env.DEV);

      // Replace `<YOUR_PRIVATE_KEY>` with your private key
      defaultClient.setPrivKey("<YOUR_PRIVATE_KEY>");
      TravelRuleApi apiInstance = new TravelRuleApi();
      TravelRuleWithdrawRequest travelRuleWithdrawRequest = new TravelRuleWithdrawRequest();
      try {
        SubmitDepositTravelRuleInfo201Response result =
            apiInstance.submitWithdrawTravelRuleInfo(travelRuleWithdrawRequest);
        System.out.println(result);
      } catch (ApiException e) {
        System.err.println("Exception when calling TravelRuleApi#submitWithdrawTravelRuleInfo");
        System.err.println("Status code: " + e.getCode());
        System.err.println("Reason: " + e.getResponseBody());
        System.err.println("Response headers: " + e.getResponseHeaders());
        e.printStackTrace();
      }
    }
  }

  ```

  ```go Go theme={null}
  package main

  import (
  	"context"
  	"fmt"
  	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
  	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
  	"os"
  )

  func main() {
  	travelRuleWithdrawRequest := *coboWaas2.NewTravelRuleWithdrawRequest("f47ac10b-58cc-4372-a567-0e02b2c3d479", coboWaas2.TravelRuleWithdrawRequest_travel_rule_info{SelfCustodyWallet: coboWaas2.NewSelfCustodyWallet(coboWaas2.DestinationWalletType("EXCHANGES_OR_VASP"), "challenge_token_abc123", "0x1234567890abcdef1234567890abcdef12345678", "0xf0a0ca69dd3afc57235c72aba3ff1f1144ee5409aeec013a9b17cdb58d0185a66a525945bfbd66e87bf0503eb0b83bf90cb973a8cbb730d19dc032e00dfe393a1c")})

  	configuration := coboWaas2.NewConfiguration()
  	// Initialize the API client
  	apiClient := coboWaas2.NewAPIClient(configuration)
  	ctx := context.Background()

  	// Select the development environment. To use the production environment, replace coboWaas2.DevEnv with coboWaas2.ProdEnv
  	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
  	// Replace `<YOUR_PRIVATE_KEY>` with your private key
  	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
  		Secret: "<YOUR_PRIVATE_KEY>",
  	})
  	resp, r, err := apiClient.TravelRuleAPI.SubmitWithdrawTravelRuleInfo(ctx).
  		TravelRuleWithdrawRequest(travelRuleWithdrawRequest).
  		Execute()
  	if err != nil {
  		fmt.Fprintf(
  			os.Stderr,
  			"Error when calling `TravelRuleAPI.SubmitWithdrawTravelRuleInfo``: %v\n",
  			err,
  		)
  		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
  	}
  	// response from `SubmitWithdrawTravelRuleInfo`: SubmitDepositTravelRuleInfo201Response
  	fmt.Fprintf(os.Stdout, "Response from `TravelRuleAPI.SubmitWithdrawTravelRuleInfo`: %v\n", resp)
  }

  ```

  ```javascript JavaScript theme={null}
  const CoboWaas2 = require("@cobo/cobo-waas2");
  // Initialize the API client
  const apiClient = CoboWaas2.ApiClient.instance;
  // Select the development environment. To use the production environment, replace `Env.DEV` with `Env.PROD`
  apiClient.setEnv(CoboWaas2.Env.DEV);
  // Replace `<YOUR_PRIVATE_KEY>` with your private key
  apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
  // Call the API
  const apiInstance = new CoboWaas2.TravelRuleApi();
  const opts = {
    TravelRuleWithdrawRequest: new CoboWaas2.TravelRuleWithdrawRequest(),
  };
  apiInstance.submitWithdrawTravelRuleInfo(opts).then(
    (data) => {
      console.log("API called successfully. Returned data: " + data);
    },
    (error) => {
      console.error(error);
    },
  );

  ```
</RequestExample>


# Authentication with Cobo OAuth
Source: https://cobo.com/developers/v2/apps/authentication

Authenticate Cobo Portal Apps with Cobo OAuth. Learn to use app keys, secrets, and Org Access Tokens for secure API requests.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This section explains how to authenticate your API requests to the WaaS service in Cobo Portal Apps using Cobo OAuth.

## Cobo OAuth vs Cobo Auth

Cobo Auth and Cobo OAuth are two authentication mechanisms. Cobo Auth identifies clients using an API key and an API secret, while Cobo OAuth identifies clients using an app key and an app secret, and controls access to resources in other organizations through an Org Access Token, along with its permissions and scopes.

* If you are developing Cobo Portal Apps for installation and use across different organizations, use Cobo OAuth to authenticate your API requests.
* If you are developing other types of apps to access data and resources within your own organization, use Cobo Auth instead. For more details about Cobo Auth, refer to [Authentication with Cobo Auth](/developers/v2/guides/overview/cobo-auth).

## With the WaaS SDK

If you are using the [WaaS SDK](/developers/v2/developer-tools/quickstart-python), you only need to provide the app secret and Org Access Token in the API request as follows:

```python theme={null}
from cobo_waas2 import Configuration, ApiClient, WalletsApi

configuration = Configuration(
    # Use `https://api.dev.cobo.com/v2` for the development environment, or `https://api.cobo.com/v2` for the production environment.
    host="https://api.dev.cobo.com/v2",
    # Replace `<APP_SECRET>` with your app secret.
    api_private_key="<APP_SECRET>",
)

client = ApiClient(configuration=configuration)
# Replace `{ORG_ACCESS_TOKEN}` with the Org Access Token.
client.set_default_header("AUTHORIZATION", f"Bearer {ORG_ACCESS_TOKEN}")
```

* To learn how to generate an app key and an app secret, see [Generate an app key and an app secret](#generate-an-app-key-and-an-app-secret).
* To learn how to get and use Org Access Tokens, refer to [Org Access Tokens](/developers/v2/apps/org-access-tokens).

## Without the WaaS SDK

If you don't use the WaaS SDK, you need to provide all the required authentication information in the request header as follows:

```javascript theme={null}
headers = {
    // Replace `{ORG_ACCESS_TOKEN}` with the Org Access Token.
    "Authorization": Bearer {ORG_ACCESS_TOKEN},
    // Replace `<APP_KEY>` with your app key.
    "Biz-Api-Key": {APP_KEY}.hex(),
    // Replace `{Nonce}` with a random string used as the request nonce.
    // This value must be the same as the value of the `TIMESTAMP` field in the API signature.
    "Biz-Api-Nonce": {Nonce},
    // Replace `{YOUR_API_SIGNATURE}` with the calculated API signature.
    "Biz-Api-Signature": {YOUR_API_SIGNATURE}.hex(),
}
```

* To learn how to generate an app key and an app secret, see [Generate an app key and an app secret](#generate-an-app-key-and-an-app-secret).
* To learn how to get and use Org Access Tokens, refer to [Org Access Tokens](/developers/v2/apps/org-access-tokens).
* To learn how to calculate the API signature using your app key, refer to [Calculate an API signature](#calculate-an-api-signature).

## App key and app secret

To ensure secure and authenticated communication between Cobo Portal Apps and the WaaS 2.0 service, a mechanism based on the app key and app secret is used. This mechanism relies on cryptographic key pairs to verify the identity of the app and the integrity of the requests.

### App key

The app key is the public key in the cryptographic key pair. It is used to identify the Cobo Portal App making the API request.

### App secret

The app secret is the private key in the key pair. It is used to sign API requests, guaranteeing their authenticity and integrity. The app secret must always remain confidential and secure to prevent unauthorized access.

The app key and app secret form a cryptographic key pair that enables secure communication with the WaaS service:

* The app key is included in API requests to identify the application to the WaaS service. It is also required in the app manifest file. For more information, refer to [Configure the manifest file](/developers/v2/apps/build-app#configure-the-manifest-file).
* The app secret signs the requests. The WaaS service verifies the signature to confirm the request's authenticity and integrity.

### Generate an app key and an app secret

This section introduces three ways to generate an app key pair (an app key and an app secret) using the Ed25519 algorithm. You can also generate app key pairs using other tools that use the Ed25519 algorithm.

The public key will be used as an app key, and the private key will be used as an app secret.

#### Use Cobo CLI

Cobo Command Line Interface (CLI) is a powerful developer tool designed to help you build, test, and manage your integration with Cobo Wallet-as-a-Service (WaaS) 2.0 directly from the command line.

1. Install Cobo CLI using the following command:

   ```shell theme={null}
   # Install Cobo CLI using pip (Python 3.9 or newer is required).
   pip install cobo-cli
   # Alternatively, you can install Cobo CLI using Homebrew.
   brew install cobo-cli
   # Test if the installation is successful
   cobo version
   ```

   For more details about the system requirements for Cobo CLI, please refer to [Install Cobo CLI](/developers/v2/developer-tools/cobo-cli/quick-start-guide#system-requirements).

2. Use the `keys generate` command to generate an app key pair using the Ed25519 algorithm as follows:

   ```shell theme={null}
   # Generate an app key pair
   cobo keys generate --key-type APP
   ```

   Generated keys are securely stored in your configuration file (default: `~/.cobo/config.toml`). For more information about this command, refer to [Key management](/developers/v2/developer-tools/cobo-cli/key-management).

#### Use OpenSSL

In a terminal window, run the following OpenSSL commands to generate a key pair using the Ed25519 algorithm:

```shell theme={null}
openssl genpkey -algorithm ed25519 -out private_key.pem

openssl pkey -in private_key.pem -pubout -out public_key.pem

echo "Private Key (Hex):"
openssl pkey -in private_key.pem -text | grep 'priv:' -A 3 | tail -n +2 | tr -d ':\n ' && echo

echo "Public Key (Hex):"
openssl pkey -pubin -in public_key.pem -text | grep 'pub:' -A 3 | tail -n +2 | tr -d ':\n ' && echo
```

You will see the output similar to the following example:

```
Private Key (Hex):
06f78882576ec0e05b1e51a33548da7e8cf958c190ba96be77b1c671f98a2b5f
Public Key (Hex):
5987dedc180167b7ab1d27e6009e5065d10d764cd85d7b64f8c968ca40326e28
```

Use the `Private Key (Hex)` as your app secret and the `Public Key (Hex)` as your app key.

#### Use a Python library

1. Install the `PyNaCl` Python library.

   In a terminal window, run the following command:

   ```shell theme={null}
   pip install PyNaCl
   ```

2. Generate a key pair.
   Import the function from the Python library to generate a key pair using the Ed25519 algorithm as follows:

   ```python theme={null}
   from nacl.signing import SigningKey
   # Create a key pair.
   sk = SigningKey.generate()
   # Print the private key in hexadecimal format.
   print("private key:", sk.encode().hex())
   # Print the public key in hexadecimal format.
   print("public key:", sk.verify_key.encode().hex())
   ```

## Calculate an API signature

The following steps introduce how to calculate an API signature.

1. First, concatenate a string based on your request as follows:
   `str_to_sign = {METHOD}|{PATH}|{TIMESTAMP}|{PARAMS}|{BODY}`

   | Field       | Description                                                                                      | Example                                                                 |
   | ----------- | ------------------------------------------------------------------------------------------------ | ----------------------------------------------------------------------- |
   | `METHOD`    | The HTTP method.                                                                                 | `GET`                                                                   |
   | `PATH`      | The API endpoint.                                                                                | `/v2/transactions/transfer`                                             |
   | `TIMESTAMP` | The nonce value. This value must be the same as the value of the `Biz-Api-Nonce` request header. | `1718587017026`                                                         |
   | `PARAMS`    | (If applicable) The query parameters.                                                            | `chain_id=ETH&limit=10`                                                 |
   | `BODY`      | (If applicable) The raw request body in string format.                                           | `{"name":"Default","wallet_subtype":"Asset","wallet_type":"Custodial"}` |

2. Use the hashlib library to perform SHA-256 hashing twice on the string as follows:
   ```python theme={null}
   import hashlib

   content_hash = hashlib.sha256(hashlib.sha256(str_to_sign.encode()).digest()).digest()
   ```

3. Use your app secret to sign the string as follows:
   ```python theme={null}
   # Replace `app_secret` with your app secret.
   sk = ed25519.SigningKey(sk_s=bytes.fromhex(app_secret))
   # Sign the hashed message
   signature = sk.sign(content_hash)
   ```

Now you've calculated an API signature.


# Build a Cobo Portal App
Source: https://cobo.com/developers/v2/apps/build-app

Build a Cobo Portal App from scratch. Follow detailed steps for development, authentication, and publishing using Cobo CLI and WaaS API.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This article walks you through the detailed steps required to build a Cobo Portal App from scratch.

For an overview of developing Cobo Portal Apps, refer to [Introduction to Cobo Portal Apps Development](/developers/v2/apps/introduction).

## Sample project

Cobo offers a sample project Hello World that allows you to quickly build a Cobo Portal App and preview it on your local machine. Refer to [Create a sample app](/developers/v2/apps/get-started) for details.

## Prerequisites

* To build and manage a Cobo Portal App, you need to first create an organization in Cobo Portal in the [development environment](https://portal.dev.cobo.com/). Follow the instructions in [Set up your account and organization](https://manuals.cobo.com/en/portal/quick-start-guide) to set up your Cobo account and create your organization. If an organization has already been set up, ask your organization admin to invite you to join the organization.
* Choose and install either FastAPI or Next.js as your development framework.

## Develop the app

### Create an app using Cobo CLI

Cobo Command Line Interface (CLI) is a powerful developer tool designed to help you build, test, and manage your integration with Cobo Wallet-as-a-Service (WaaS) 2.0 directly from the command line.

1. Install Cobo CLI using the following command:

   ```shell theme={null}
   # Install Cobo CLI using pip (Python 3.9 or newer is required).
   pip install cobo-cli
   # Alternatively, you can install Cobo CLI using Homebrew.
   brew install cobo-cli
   # Test if the installation is successful
   cobo version
   ```

   For more details about the system requirements for Cobo CLI, please refer to [Install Cobo CLI](/developers/v2/developer-tools/cobo-cli/quick-start-guide#system-requirements).

2. Log in to Cobo Portal and connect Cobo CLI to your Cobo Portal account. You can choose one of the [three authentication methods](/developers/v2/developer-tools/cobo-cli/login-and-authentication) to authenticate. As an example, this step will show you how to authenticate with your Cobo Portal account:

   ```shell theme={null}
   # Use your Cobo Portal account to authenticate.
   cobo auth user
   # Initiate the user login process.
   cobo login
   ```

   You'll be prompted to open a browser to continue the authorization process. Complete the authorization process in your browser, granting the necessary permissions for Cobo CLI to access your crypto wallets. For more details about authentication methods, see [Login and authentication](/developers/v2/developer-tools/cobo-cli/login-and-authentication).

3. Use the [app init](/developers/v2/developer-tools/cobo-cli/app-init) command to create a Hello World app project. You can specify the details of the WaaS application you want to create through options, or choose these parameters step by step and create the project using the prompts of Cobo CLI.

   The following command creates a Cobo Portal App project, using Org Access Tokens for authentication, and creates it in the directory named `hello_world`:

   ```shell theme={null}
   cobo app init --app-type portal --auth org --directory hello_world
   ```

### Acquire authentication information

To authenticate your API requests to the WaaS service in Cobo Portal Apps, you need to provide your app key and Org Access Token. You also need to calculate an API signature if you are not using the [WaaS SDK](/developers/v2/developer-tools/quickstart-python). Refer to [Cobo OAuth](https://www.cobo.com/developers/v2/apps/authentication) for how to acquire all the necessary information for authentication.

### Verify app users

User Info Tokens are JSON Web Tokens (JWTs) signed by Cobo Portal. These tokens allow Cobo Portal Apps to retrieve information about users, including their user ID, email address, and permissions. A Cobo Portal App can use the information to verify a user's identity and control their access to the organization's resources based on the permissions. It is recommended that you verify a user's identity before they can get started using the app. For more information, refer to [User Info Tokens](/developers/v2/apps/verify-users).

### Call the WaaS API

You can now call the WaaS 2.0 API to build features for your app. When calling an API operation, you need to provide the required authentication information in the request header.

The following code snippets show how to list all the wallets in an organization using the [WaaS Python SDK](/developers/v2/developer-tools/quickstart-python).

```python theme={null}
from cobo_waas2 import Configuration, ApiClient, WalletsApi

configuration = Configuration(
    # Use `https://api.dev.cobo.com/v2` for the development environment, or `https://api.cobo.com/v2` for the production environment.
    host="https://api.dev.cobo.com/v2",
    # Replace `<APP_SECRET>` with your app secret.
    api_private_key=<APP_SECRET>,
)
client = ApiClient(configuration=configuration)
# Replace `{ORG_ACCESS_TOKEN}` with the Org Access Token.
client.set_default_header("AUTHORIZATION", f"Bearer {ORG_ACCESS_TOKEN}")
api_instance = WalletsApi(client)
wallets = api_instance.list_wallets(wallet_type=WalletType.CUSTODIAL).data
```

For details about each API operation, refer to [the API reference](/developers/v2/api-references).

### Configure the manifest file

Before you publish the app, you need to fill out the manifest file, which contains the app's configuration information. Refer to the following table for field descriptions and examples.

<table>
  <thead>
    <tr>
      <th>Field</th>
      <th>Description</th>
      <th>Example</th>
    </tr>
  </thead>

  <tbody>
    <tr>
      <td>app\_name</td>
      <td>The app name.</td>
      <td><code>SuperLoop</code></td>
    </tr>

    <tr>
      <td>app\_desc</td>
      <td>A brief description of the app, with a maximum length of 80 characters.</td>
      <td><code>SuperLoop is an off-exchange settlement network that allows institutions to trade on exchanges without worrying about counterparty risks.</code></td>
    </tr>

    <tr>
      <td>app\_desc\_long</td>
      <td>A detailed description of the app, including use cases and key features. <p>The description must be under 1000 characters and formatted in Markdown.</p></td>
      <td><code>SuperLoop is an off-exchange settlement network that allows institutions to trade on exchanges without worrying about counterparty risks. For asset managers, trading on exchanges can be conducted with greater confidence and efficiency. The need to pre-fund on exchanges before trading is eliminated, minimizing counterparty risks.</code></td>
    </tr>

    <tr>
      <td>app\_icon\_url</td>
      <td>The URL of the app icon. <p>Please contact our Operation team at <a href="mailto:help@cobo.com">[help@cobo.com](mailto:help@cobo.com)</a> to help you upload the app icon.</p></td>
      <td><code>[https://d.cobo.com/public/logos/Logo.png](https://d.cobo.com/public/logos/Logo.png)</code></td>
    </tr>

    <tr>
      <td>screen\_shots</td>
      <td>The URLs of at least three screenshots showcasing key features. <p>Please contact our Operation team at <a href="mailto:help@cobo.com">[help@cobo.com](mailto:help@cobo.com)</a> to help you upload the screenshots.</p></td>
      <td><code>"[https://d.cobo.com/apk/android/SuperLoop.png](https://d.cobo.com/apk/android/SuperLoop.png)", "[https://d.cobo.com/apk/android/Loop.png](https://d.cobo.com/apk/android/Loop.png)", "[https://d.cobo.com/apk/android/MirrorModal.png](https://d.cobo.com/apk/android/MirrorModal.png)"</code></td>
    </tr>

    <tr>
      <td>required\_permissions</td>
      <td>A list of the permissions required for the app to access resources within users' organizations. <p>A permission consists of a resource type and an operation, separated by a comma. For example, <code>wallet:create</code> represents the permission to create a wallet.</p>For the full list of permissions in WaaS 2.0, refer to <a href="https://www.cobo.com/developers/v2/guides/overview/permission-list">Permissions list</a>.</td>
      <td><code>"wallet:create", "transaction:withdraw", "mpc\_project:update"</code></td>
    </tr>

    <tr>
      <td>optional\_permissions</td>
      <td>(Optional) A list of permissions that the app can request to access additional resources within users' organizations. <p>These are not mandatory but may enhance app functionality. A permission consists of a resource type and an operation, separated by a comma. For example, <code>wallet:create</code> represents the permission to create a wallet.</p>For the full list of permissions in WaaS 2.0, refer to <a href="https://www.cobo.com/developers/v2/guides/overview/permission-list">Permissions list</a>.</td>
      <td><code>"address\_book:create", "kyc\_profile:read", "team\_member:freeze"</code></td>
    </tr>

    <tr>
      <td>homepage\_url</td>
      <td>The host URL of the app homepage, used to embed the app into Cobo Portal via an iframe.</td>
      <td><code>[https://example.com](https://example.com)</code></td>
    </tr>

    <tr>
      <td>callback\_urls</td>
      <td>The URL of the endpoint used to receive the callback after the organization admin approves the app's request for permissions.</td>
      <td><code>[https://example.com/webhooks/organization/authorization](https://example.com/webhooks/organization/authorization)</code></td>
    </tr>

    <tr>
      <td>client\_key</td>
      <td>The app key. <p>For instructions on how to generate an app key, refer to <a href="https://www.cobo.com/developers/v2/apps/authentication#generate-an-app-key-and-an-app-secret">Generate an app key and an app secret</a>.</p></td>
      <td><code>AbCdEfGhIjKlMnOpQrStUvWxYz1234567890</code></td>
    </tr>

    <tr>
      <td>creator\_name</td>
      <td>The developer's name.</td>
      <td><code>Cobo</code></td>
    </tr>

    <tr>
      <td>contact\_email</td>
      <td>The developer's contact email.</td>
      <td><code>[sample@email.com](mailto:sample@email.com)</code></td>
    </tr>

    <tr>
      <td>operation\_approval\_rules</td>
      <td>(Optional) The app's default approval workflows. To use this feature, the `required_permissions` field must be contain `app_governance_policy:update` and `app_governance_policy:read`. For how to configure approval workflows, refer to <a href="https://www.cobo.com/developers/v2/apps/configure-workflow">Configure approval workflows</a>.</td>
      <td><code>\[\{"operation\_id": "25cbb115-82a1-4474-9993-538bb439ad33", "operation\_name": "Make Batch Payout", "default\_approval\_policies": \[\{"action": \{"type": "Quorum", "content": \{"roles": \["admin"], "threshold": 1, "type": "PART\_APPROVAL"}}, "conditions": \[\{"field": "amount", "value\_type": "INT", "value": "100", "operator": ">"}]}, \{"action": \{"type": "Accept", "content": ""}, "conditions": null}], "descriptions": \[\{"field": "amount", "description": "Total USD amount", "value\_type": "INT", "display\_name": "Total Amount(USD)"}]}]</code></td>
    </tr>

    <tr>
      <td>wallet\_type</td>
      <td>(Optional) The wallet types supported by the app. The possible values are as follows: <ul><li><code>Custodial</code></li><li><code>MPC</code></li><li><code>Exchange</code></li><li><code>User-Controlled</code></li><li><code>Org-Controlled</code></li><li><code>Asset</code></li><li><code>Main</code></li></ul> For example, if this field is set to <code>Custodial, MPC</code>, users will only be able to select these wallet types as the wallet scope that the app can access. <p>If this field is left empty, users can select any wallet type available.</p>For the full list of wallet scopes in WaaS 2.0, refer to <a href="https://www.cobo.com/developers/v2/guides/overview/permissions-and-scopes#wallet-scopes">Wallet scopes</a>.</td>
      <td><code>"Custodial", "MPC"</code></td>
    </tr>

    <tr>
      <td>is\_policy\_reminded</td>
      <td>(Optional) Whether app users will be reminded of setting up transaction policies for the app. <p>The default value is <code>true</code>.</p></td>
      <td><code>true</code></td>
    </tr>
  </tbody>
</table>

Refer to the following screenshots for where these fields will display on the app UI.

**The Apps page**

<img alt="The Apps page" />

**The Overview tab of the App Details page**

<img alt="The Overview tab of the App Details page" />

**The Permissions tab of the App Details page**

<img alt="The Permissions tab of the App Details page" />

## Publish the app

When you have completed developing your app, you can use the [app upload](/developers/v2/developer-tools/cobo-cli/app-upload) Cobo CLI command to publish the app to the production environment or development environment:

```shell theme={null}
cobo app upload
```

<Info>For more information about how to switch between development and production environments, refer to [Environment management](/developers/v2/developer-tools/cobo-cli/environment-management).</Info>

Before publishing your Cobo Portal Apps, ensure the following:

* Verify the [app manifest file](/developers/v2/apps/build-app#configure-the-manifest-file) is configured correctly.
* Log into Cobo CLI with your Cobo Portal account.
* Generate an app key if you haven't done so. For more details, refer to [Generate keys](/developers/v2/developer-tools/cobo-cli/key-management#generate-keys).
* Run the command from the project directory where the manifest file is located.

If you publish your app to the production environment, the command will automatically trigger a workflow that requires approval from Cobo. The approval result will be sent as an email to the `contact_email` configured in the manifest file. Once approved, your app will be available to all users on Cobo Portal.

If you publish your app to the development environment, no approval is required and your app will be available only to the users in your organization.

The `app upload` command will generate a client ID for your app in the manifest file. A client ID is a unique identifier for a Cobo Portal App and cannot be modified after being generated. It is required for getting the Org Access Token. For more details, refer to [Org Access Tokens](/developers/v2/apps/org-access-tokens).

An app can be published only once, otherwise an error will occur. For subsequent updates, you need to follow the process of [updating the app](#update-the-app).

## Update the app

If you want to update your app after it's published, you can implement the changes and then use the [app update](/developers/v2/developer-tools/cobo-cli/app-update) Cobo CLI command:

```shell theme={null}
cobo app update
```

Before updating your Cobo Portal Apps, ensure the following:

* Verify the [app manifest file](/developers/v2/apps/build-app#configure-the-manifest-file) is configured correctly.
* Log into Cobo CLI with your Cobo Portal account.
* Run the command from the project directory where the manifest file is located.

Similar to publishing an app, if you update an app in the production environment, the update command will automatically trigger a workflow that requires approval from Cobo. Otherwise, if you update an app in the development environment, no approval is required.


# Configure approval workflow
Source: https://cobo.com/developers/v2/apps/configure-workflow

Configure approval workflows in Cobo Portal Apps. Learn to set rules, manage operations, and ensure secure transaction approvals.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This section introduces how to configure approval workflows for your Cobo Portal Apps.

In the context of Cobo Portal Apps, an approval workflow consists of specific operations on the app, such as submitting a transaction or initiating a payout, that will trigger certain approval rules. When users install an app, the app will be automatically configured with default approval workflows, which are defined in the app manifest file. For more details about how the approval workflow affects the app UI, refer to <a href="https://manuals.cobo.com/en/portal/portal-apps/workflow">View and update approval workflows</a>.

You can configure the default approval workflow for your app in the `operation_approval_rules` field in the app manifest file. The following is an example of the `operation_approval_rules` object. This object is defined in the [Batch Payout](https://manuals.cobo.com/en/apps/batch-payouts/introduction) app's manifest file, which configures the default approval workflow for the app. If you make a batch payout in the Batch Payout app, and the payout amount is greater than \$100, you will trigger an approval workflow in which the batch payout requires approval from one organization admin. The payout request will be in the Pending Approval status until an admin approves or rejects.

```json theme={null}
[
    {
        // The unique ID of the approval workflow. 
        // It must be unique within the app and not exceed 64 characters in length.
        "operation_id": "25cbb115-82a1-4474-9993-538bb439ad33",
        // The name of the approval workflow that will be displayed on the UI.
        "operation_name": "Make Batch Payout",
        // The details of the approval workflow. The maximum length of this field is 10,000 characters.
        "default_approval_policies": [
            {
                // The approval actions triggered once the conditions are met.
                "action": {
                    // The action type. Possible values include:
                    // `Accept`: Automatically approve the operation.
                    // `Reject`: Automatically reject the operation.
                    // `Quorum`: Need at least a specific user role to approve.
                    "type": "Quorum",
                    // The details of the `Quorum` action.
                    // This field is applicable only when `type` is `Quorum`.
                    // - roles: The user roles that can approve. It must be lowercase.
                    // - threshold: Approval threshold. Applicable only when `type` is `PART_APPROVAL`.
                    // If the threshold is not met, the operation will remain in a pending state until the required approvals are obtained.
                    // - type: Approval type. Possible values include:
                    // - `PART_APPROVAL`: Need part of user roles to approve.
                    // - `FULL_APPROVAL`: Need all user roles to approve.
                    "content": "{\"roles\": [\"admin\"], \"threshold\": 2, \"type\": \"PART_APPROVAL\"}"
                },
                // Conditions that will trigger the approval actions.
                "conditions": [
                    {
                        // The field value serves as the key of the field.
                        "field": "amount",
                        // The field value type. Possible values include:
                        // `INT`: Integer
                        // `FLOAT2`: Floating-point number with two decimal places
                        "value_type": "INT",
                        // The value of the field. 
                        // If `value_type` is `FLOAT2`, set the value as `100.00`.
                        "value": "100",
                        // The operator type. Possible values include `>`, `>=`, `=`, `<`, and `<=`.
                        "operator": ">"
                    }
                ]
            },
            // Please keep this structure.
            {
                "action": {
                    "type": "Accept",
                    "content": ""
                },
                "conditions": null
            }
        ],
        // The text of the `condition` fields that will be displayed on the UI.
        // The `descriptions` fields must contain the elements in the `conditions` field.
        "descriptions": [
            {
                // The field value that must be the same as the `field` in `conditions`.
                "field": "amount",
                // The description of the field on the UI. 
                "description": "Total USD amount",
                // The value of the field that must be the same as the `value_type` in `conditions`.
                "value_type": "INT",
                // Display name of the field on the UI.
                "display_name": "Total Amount(USD)"
            }
        ]
    },
    {
        // Create more approval workflows with the same structure as above.
        ...
    }
]
```

<Info>For more details about user roles, refer to [User roles](/developers/v2/guides/overview/permissions-and-scopes#user-roles).</Info>

The following is a screenshot of the approval workflow fields on the UI.

<img alt="The Edit Approval Workflow dialog" />


# Create a sample app
Source: https://cobo.com/developers/v2/apps/get-started

Start building a Cobo Portal App with our step-by-step guide. Learn to set up, preview, and publish using Cobo CLI.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This article guides you through creating a sample Cobo Portal App using a template and previewing it locally.

## Prerequisites

* To build and manage a Cobo Portal App, you need to first create an organization in Cobo Portal in the [development environment](https://portal.dev.cobo.com/). Follow the instructions in [Set up your account and organization](https://manuals.cobo.com/en/portal/quick-start-guide) to set up your Cobo account and create your organization. If an organization has already been set up, ask your organization admin to invite you to join the organization.
* Install FastAPI as the development environment.

## Create an app project using Cobo CLI

Cobo Command Line Interface (CLI) is a powerful developer tool designed to help you build, test, and manage your integration with Cobo Wallet-as-a-Service (WaaS) 2.0 directly from the command line.

1. Install Cobo CLI using the following command:

   ```shell theme={null}
    # Install Cobo CLI using pip (Python 3.9 or newer is required).
    pip install cobo-cli
    # Alternatively, you can install Cobo CLI using Homebrew.
    brew install cobo-cli
    # Test if the installation is successful
    cobo version
   ```

   For more details about the system requirements for Cobo CLI, please refer to [Install Cobo CLI](/developers/v2/developer-tools/cobo-cli/quick-start-guide#system-requirements).

2. Log in to Cobo Portal and connect Cobo CLI to your Cobo Portal account. You can choose one of the [three authentication methods](/developers/v2/developer-tools/cobo-cli/login-and-authentication) to authenticate. As an example, this step will show you how to authenticate with your Cobo Portal account:

   ```shell theme={null}
   # Use your Cobo Portal account to authenticate.
   cobo auth user
   # Initiate the user login process.
   cobo login
   ```

   You'll be prompted to open a browser to continue the authorization process. Complete the authorization process in your browser, granting the necessary permissions for Cobo CLI to access your crypto wallets. For more details about authentication methods, see [Login and authentication](/developers/v2/developer-tools/cobo-cli/login-and-authentication).

3. Use the [app init](/developers/v2/developer-tools/cobo-cli/app-init) command to create a sample app based on a template. You can specify the details of the WaaS application you want to create through options, or choose these parameters step by step and create the project using the prompts of Cobo CLI.

   The following command creates a Cobo Portal App project, using Org Access Tokens for authentication, and creates it in the directory named `hello_world`:

   ```shell theme={null}
   cobo app init --app-type portal --auth org --directory hello_world
   ```

## Run and preview the app

1. Start the frontend server.
   Navigate to the `frontend` folder in the directory where you created the app project and run the following command:

   ```shell theme={null}
   npm install
   npm start
   ```

   Now you can view the app's frontend as the following screenshot shows:

   <img alt="The frontend preview" />

2. Start the backend server.
   Navigate to the `backend` folder in the directory where you created the app project and run the following command:

   ```shell theme={null}
   uvicorn main:app --reload
   ```

   Now you can view the app's backend as the following screenshot shows:

   <img alt="The backend preview" />

   To display the wallets and transactions in your organization, you need to complete the following steps:

   * Find the `.env.example` file in the `backend` folder and rename it to `.env`. In the `.env` file, set `COBO_API_KEY` as your API key, `COBO_API_SECRET` as your API secret, and set `COBO_ENV` as `dev` or `production` based on the environment you use. For more information about API keys, refer to [API key](/developers/v2/guides/overview/cobo-auth#api-key).
   * Register your API key on Cobo Portal. For more details, refer to [Register an API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key).

   After you complete the above steps, you can view the wallets and transactions as the following screenshot shows:

   <img alt="The frontend preview with wallets and transactions" />

## Publish the app

If you want to publish the app to Cobo Portal, you can use the [app upload](/developers/v2/developer-tools/cobo-cli/app-upload) Cobo CLI command to publish the app to the production environment or development environment. For more details, refer to [Publish the app](/developers/v2/apps/build-app#publish-the-app).


# Introduction to Cobo Portal App development
Source: https://cobo.com/developers/v2/apps/introduction

Explore Cobo Portal App development with WaaS 2.0 API, Cobo CLI, and Cobo UI toolkit.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Cobo Portal Apps are extensions of [Cobo Portal](https://manuals.cobo.com/en/portal/introduction). They can exist as iframe elements within Cobo Portal or as bots in the form of APIs and webhooks. By leveraging tools including the [Cobo Wallet-as-a-Service (WaaS) 2.0 API](/developers/v2/guides/overview/introduction), developers like you can build Cobo Portal Apps to significantly expand the capabilities of Cobo Portal, such as staking, trading, automating finance operations, and more.

User can easily explore Cobo Portal Apps by visiting [Cobo Portal](https://portal.cobo.com/apps). To learn more about publicly available Cobo Portal Apps, see [Introduction to Cobo Portal Apps](https://manuals.cobo.com/en/portal/portal-apps/introduction).

<img alt="cobo portal app homepage" />

## Tools you can leverage

Cobo offers the following tools that allow you to develop a Cobo Portal App with ease.

### WaaS 2.0 API

The [WaaS 2.0 API](/developers/v2/api-references/playground) is the latest version of Cobo's WaaS API offering. It enables a Cobo Portal App to interact with users' wallets, including:

* Querying information, such as wallet specifics, balances, and transaction history.
* Managing wallets, such as transferring tokens and calling smart contracts.
* Subscribing to webhook events to receive notifications.

The API uses [Cobo OAuth](/developers/v2/apps/authentication) to authorize a Cobo Portal App to access other organizations' data and perform operations on the organizations' wallets.

### Cobo CLI

Cobo CLI is a developer tool that allows you to build, test, and publish Cobo Portal Apps directly from the command line. With Cobo CLI, you can easily handle common tasks such as creating, publishing, and updating an app.

### Cobo UI toolkit

The Cobo UI toolkit is a library of pre-built components that adhere to Cobo Portal's design and visual standards. You can leverage the toolkit to quickly build a user interface for your Cobo Portal Apps.

## Related links

* Cobo offers a Hello World sample project that showcases how to quickly build a Cobo Portal App. Refer to [Get started with Cobo Portal Apps](/developers/v2/apps/get-started) for details.
* For a step-by-step guide on how to build a Cobo Portal App from scratch, refer to [Build an Cobo Portal App](/developers/v2/apps/build-app).


# Org Access Tokens
Source: https://cobo.com/developers/v2/apps/org-access-tokens

Discover how Org Access Tokens enable secure resource access in Cobo Portal Apps. Learn token acquisition, refresh, and permission management.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

When a Cobo Portal App needs to access the resources of an organization, the Org Access Token signals to the WaaS service that the app has received approval from the organization admin to access certain resources.

For security purposes, Org Access Tokens will expire after a certain amount of time. The app can use a Refresh Token to get a new Org Access Token.

## How it works

```mermaid theme={null}
sequenceDiagram
    participant User
    participant Organization Admin
    participant Cobo Portal
    participant WaaS 2.0 Service
    participant Cobo Portal App
  

    User->>Cobo Portal: Requests to install a Cobo Portal App
    Cobo Portal->>Organization Admin: Requests to grant permissions
    Organization Admin->>Cobo Portal: Approves to grant permissions on Cobo Guard

    
    Cobo Portal->>Cobo Portal App: Notifies permissions granted by Organization Admin
    Cobo Portal App->>WaaS 2.0 Service: Requests Org Access Token
    WaaS 2.0 Service->>Cobo Portal App: Provides Org Access Token
    Cobo Portal App->>WaaS 2.0 Service: Accesses service with Org Access Token
    Cobo Portal App->>WaaS 2.0 Service: Refreshes Org Access Token with Refresh Token
    User->>Cobo Portal App: Uses the Cobo Portal App
```

1. A user under an organization installs your app on Cobo Portal. During the installation process, the user selects the permissions granted to your app and the wallets your app is allowed to interact with.
   <Note>If a user updates the permission settings after the app is installed, it will require approval from the organization admin, and the app will need to request a new Org Access Token, just as it does during the app installation.</Note>
2. Cobo Portal sends an approval request to the organization admin, asking for permissions and access to wallets selected by the user.
3. The organization admin approves the request on Cobo Guard.
4. Cobo Portal sends a callback message that contains the organization ID and approval result to the callback URL that you provide in the manifest file.
5. Your app acquires an Org Access Token from the WaaS service by calling the [Get Org Access Token](/developers/v2/api-references/oauth/get-org-access-token) operation.
6. Your app accesses the WaaS 2.0 service with the Org Access Token.
7. When the Org Access Token expires, your app calls the [Refresh Org Access Token](/developers/v2/api-references/oauth/refresh-org-access-token) operation to get a new Org Access Token with the Refresh Token. Otherwise API requests will return a `500` error.
   <Note>The expiration time for Refresh Tokens is currently set to 30 days and is subject to change. If the Refresh Token expires, users will need to reinstall the app, following the same process as when installing a new app.</Note>
8. Users use your app to interact with the selected wallets using the permissions granted.

The Org Access Token is associated with the permissions granted by the organization admin. Each permission is a combination of an operation and a resource type. Your app can only perform the specified operations on the corresponding resource types.

## Acquire Org Access Tokens

Your app will need to call [Get access token](/developers/v2/api-references/oauth/get-org-access-token) to get Org Access Tokens and call [Refresh access token ](/developers/v2/api-references/oauth/refresh-org-access-token)to refresh Org Access Tokens when they expire. When calling these two operations, your app must provide the app key, client ID, and organization ID as inputs.

### 1. Generate an app key

An app key is used to authenticate the Cobo Portal App when it makes an API request to the WaaS service. For how to generate an app key, refer to [Generate an app key](/developers/v2/apps/authentication#generate-an-app-key).

### 2. Retrieve the client ID

When an app is published, Cobo generates a client ID for your app, which can be found in the manifest file. For how to get the client ID, refer to [Publish the app](/developers/v2/apps/build-app#publish-the-app).

### 3. Retrieve the organization ID

When a user installs an app on Cobo Portal and the organization admin has granted the permissions, a callback message will be sent to the configured endpoint `callback_url`configured in the manifest file. The callback message includes the approval result and the ID of the user's organization.

A sample callback message is as follows:

```
POST <callback_url>?approval_result=1&org_id=ba3b0323-7000-4278-8cf4-92ad4ae96b74
```

Currently, the `approval_result` parameter has the following possible values:

* `1`: A user in the organization installed the app, and the organization admin approved the permissions granted by the user.
* `2`: After the app was installed, a user in the organization updated the app settings, including required permissions, optional permissions, and wallet scopes, and the organization admin approved the updates.

### 4. Call the Get access token operation

Call the [Get access token](/developers/v2/api-references/oauth/get-org-access-token) operation to get an Org Access Token and call the [Refresh access token](/developers/v2/api-references/oauth/refresh-org-access-token)operation to refresh the Org Access Token when it expires.

The following sample code shows how to get an Org Access Token with the Python SDK.

```python theme={null}
from cobo_waas2 import Configuration, ApiClient, OAuthApi

configuration = Configuration(
  # Use https://api.dev.cobo.com/v2 if your app needs to access an organization's resources in the development environment, or use https://api.cobo.com/v2 for the production environment.
  host="https://api.dev.cobo.com/v2",
  # Replace `<APP_SECRET>` with your app secret
  api_private_key=<APP_SECRET>,
)

client = ApiClient(configuration=configuration)
api_instance = OAuthApi(client)
org_token = api_instance.get_token(
  # Replace <CLIENT_ID> with the client ID of your app.  
  client_id=<CLIENT_ID>,
  # Replace `<ORG_ID>` with the ID of the organization that your app wants to access.
  org_id=<ORG_ID>,
  grant_type="org_implicit",
)
```

A sample Org Access Token is as follows:

```json theme={null}
{
 "access_token": "wu0Wx4jv9SOKzPXt15APApEpbJqGvi9sowUDPi5G9pUZvQgZxxLYfoEvMFFIMMYz",
 "token_type": "Bearer",
 "scope": "",
 "expires_in": 43199,
 "refresh_token": "AMLABEIz4GgFknxniMEj2TTILXCqc6bXYKmrHg4Ms6TSjGGbPX4ipz5xFrcErmGg"
}
```


# User Info Tokens
Source: https://cobo.com/developers/v2/apps/verify-users

Learn how to use User Info Tokens in Cobo Portal Apps to verify user identity and control access with JWTs.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

User Info Tokens are JSON Web Tokens (JWTs) signed by Cobo Portal. These tokens allow Cobo Portal Apps to retrieve information about users, including their user ID, email address, and permissions. A Cobo Portal App can use the information to verify a user's identity and control their access to the organization's resources based on the permissions.

## How it works

```mermaid theme={null}
sequenceDiagram
    participant Cobo Portal
    participant Cobo Portal App
    participant User
    
    User->>Cobo Portal: Opens Cobo Portal App
    Cobo Portal->>Cobo Portal App: Renders the app in an iframe
    Cobo Portal App->>Cobo Portal: Requests User Info Token
    Cobo Portal->>Cobo Portal App: Provides User Info Token
    Cobo Portal App->>Cobo Portal: Requests JWKS
    Cobo Portal->>Cobo Portal App: Provides JWKS
    Cobo Portal App->>Cobo Portal App: Decodes and verifies User Info Token with JWKS
```

1. A user opens a Cobo Portal App on Cobo Portal.
2. Cobo Portal renders the app in an iframe.
3. The app requests a User Info Token from Cobo Portal.
4. Cobo Portal provides the User Info Token.
5. The app requests JSON Web Key Set (JWKS) from Cobo Portal.
6. Cobo Portal provides the JWKS.
7. The app decodes and verifies the User Info Token using the JWKS.
   <Note>Please use the algorithm specified in the `alg` field of the JWT header to perform the verification.</Note>

## Request a User Info Token

To obtain a User Info Token, follow these steps:

1. Install Cobo UI Toolkit by running the following command:
   ```shell theme={null}
   npm install cobo-ui-toolkit
   ```
2. Use the `getAuthInfo` function provided by Cobo UI Toolkit:
   ```javascript theme={null}
   import { getAuthInfo } from 'cobo-ui-toolkit';


   const authInfo = await getAuthInfo();

   /*
   type AuthInfo = {
       // The User Info Token
       token: string;
       // The organization ID of the user
       orgID: string;
       // The user ID
       userID?: string;
   };
   */

   if (authInfo.data) {
       // Handle the User Info Token.
       // Handle the organization ID.
   } else if (authInfo.error) {
       // Handle errors.
   }
   ```

Here is an example of what a decoded User Info Token looks like:

```json theme={null}
{
    "sub": "1234",
    "email": "dev@cobo.com",
    "role_names": [
        "Viewer",
        "Spender",
        "Approver",
        "Operator",
        "Admin"
    ],
    "iss": "https://portal.dev.cobo.com/",
    "iat": 1723705170,
    "exp": 1723705470,
    "jti": "6a02090be57a4718bc1b0a3914d70584",
    "aud": "I5rK1KnSA9xtIbIrqdzJLVPrTc0EsaGG"
}
```

## Validate a User Info Token

Validate the User Info Token with the JWKS. To retrieve JWKS, send an HTTP GET request to the appropriate URL based on the environment in which your app is used:

* Production environment: `https://api.cobo.com/v2/oauth/authorize/jwks.json`
* Development environment: `https://api.dev.cobo.com/v2/oauth/authorize/jwks.json`

Additionally, you need to verify the `iss` (issuer), `exp` (expiration ), and `aud` (audience) fields are correct.


# View API documentation
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/api-documentation

Fetch and update the latest WaaS 2.0 OpenAPI specification with Cobo CLI for up-to-date API definitions.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use this command to fetch and update the latest WaaS 2.0 OpenAPI specification. Cobo CLI downloads the YAML file and saves it to your local configuration directory, ensuring you have the most up-to-date API definitions.

## Usage

```shell theme={null}
cobo doc <topic_or_path> [options]
```

## Arguments

`<topic_or_path>`: Specifies the documentation topic or the API operation path. Possible values include:

* `guides`: (Default)Opens the [Introduction to WaaS 2.0](/developers/v2/guides/overview/introduction) guide.
* `api`: Opens the [API Reference](/developers/v2/api-references/playground) page.
* `sdk`: Opens the [WaaS SDKs](/developers/v2/developer-tools/quickstart-python) guide.
* `apps`: Opens the [Cobo Portal App development](/developers/v2/apps/introduction) guide.
* API endpoint paths: Displays detailed information on API operations available for the specified path such as `/wallets`.

## Options

`-u`, `--update`: Update the OpenAPI specification for WaaS 2.0, ensuring you have the latest API definitions and documentation. With this option used, this command will only perform the updates and then exit. After a successful update, Cobo CLI confirms the operation with a "specification file downloaded successfully" message.

## Example

```shell theme={null}
cobo doc /wallets/mpc/vaults
```

This command fetches the documentation of the `/wallets/mpc/vaults` endpoint, including its description, parameters, and response format.


# Create a WaaS application
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/app-init

Use the `init` command to create and configure a WaaS application with Cobo CLI, specifying app type and frameworks.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use the `init` command to create an application that integrates the WaaS 2.0 service.

You can specify the details of the WaaS application you want to create through options, including the application type, authentication method, and development frameworks. You can also choose these parameters step by step and create the project using the prompts of Cobo CLI.

## Usage

```shell theme={null}
cobo app init [options]
```

## Options

* `-t`, `--app-type <portal|web|mobile|automation>`: The type of WaaS application. Possible values include:
  * `portal`: [Cobo Portal Apps](/developers/v2/apps/introduction)
  * `web`: Web applications
  * `mobile`: Mobile applications
  * `automation`: AI agents for automating tasks or processes

* `--auth <apikey|org|user>`: The authentication method that the application uses to access the WaaS 2.0 service. Possible values include:
  * `apikey`: [API keys](/developers/v2/guides/overview/cobo-auth#api-key)

  * `org`: [Org Access Tokens](/developers/v2/apps/org-access-tokens)

    <Note>If you are creating a Cobo Portal App, you need to use Org Access Tokens as the authentication method.</Note>

  * `user`: Cobo Portal accounts

* `--wallet-type <custodial-asset|custodial-web3|mpc-org-controlled|mpc-user-controlled|exchange>`: The wallet type that the application interacts with. Possible values include:
  * `custodial-asset`: Custodial Wallets (Asset Wallets)
  * `custodial-web3`: Custodial Wallets (Web3 Wallets)
  * `mpc-org-controlled`: MPC Wallets (Organization-Controlled Wallets)
  * `mpc-user-controlled`: MPC Wallets (User-Controlled Wallets)
  * `exchange`: Exchange Wallets

    <Note>Currently this parameter does not affect the application to be created.</Note>

* `--mobile <flutter|react-native|kotlin|swift>`: The mobile development framework of the application. Possible values include:
  * `flutter`: Flutter
  * `react-native`: React Native
  * `kotlin`: Kotlin
  * `swift`: Swift

* `--web <react|nextjs|vue|svelte>`: The web development framework of the application. Possible values include:
  * `react`: React
  * `nextjs`: Next.js
  * `vue`: Vue
  * `svelte`: Svelte
    <Note>Currently Cobo CLI only supports `react`.</Note>

* `--backend <fastapi|django|express|flask|spring-boot|gin|laravel|rails|nextjs>`: The backend development framework of the application. Possible values include:
  * `fastapi`: FastAPI
  * `django`: Django
  * `express`: Express
  * `flask`: Flask
  * `spring-boot`: Spring Boot
  * `gin`: Gin
  * `laravel`: Laravel
  * `rails`: Ruby on Rails
  * `nextjs`: Next.js
    <Note>Currently Cobo CLI only supports `fastapi`.</Note>

* `-d`, `--directory <DIRECTORY>`: The directory in which you want to create the application project.

* `-f`, `--force`: Force overwrite the project directory if it already exists.

<Note>If you use the prompts of Cobo CLI to create the application, you can skip the app key step for now if you have not generated an app key.</Note>

## Example

```shell theme={null}
cobo app init --app-type web --auth org --directory my_project
```

This command initializes a new WaaS application project of the `web` type (indicating a web application), using Org Access Tokens for authentication, and creates it in the directory named `my_project`.


# Check Cobo Portal App status
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/app-status

Use the `app status` command to verify the current status of your Cobo Portal Apps in production.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

If you publish or update your Cobo Portal Apps in the production environment, a workflow is automatically triggered that requires approval from Cobo. Once approved, your app will be available to all users on Cobo Portal. You can use the `status` command to check the status of Cobo Portal Apps.

Ensure that you run the command from the project directory where the manifest file is located.

## Usage

```shell theme={null}
cobo app status
```

## Example

```shell theme={null}
cobo app status
```

This command displays the App ID and current status of the Cobo Portal App.


# Update Cobo Portal Apps
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/app-update

Deploy updates to your Cobo Portal App using the `app update` command to keep your app current.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use the `app update` command to deploy updates to a Cobo Portal App on Cobo Portal. For more details about updating a Cobo Portal App, refer to [Update the app](/developers/v2/apps/build-app#update-the-app).

Before updating your Cobo Portal Apps, ensure the following:

* Verify the [app manifest file](/developers/v2/apps/build-app#configure-the-manifest-file) is configured correctly.
* Log into Cobo CLI with your Cobo Portal account.
* Run the command from the project directory where the manifest file is located.

## Usage

```shell theme={null}
cobo app update
```

## Example

```shell theme={null}
cobo app update
```

This command updates a Cobo Portal App with the latest changes.


# Publish Cobo Portal Apps
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/app-upload

Use the `app upload` command to publish your Cobo Portal Apps to Cobo Portal efficiently.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use the `app upload` command to publish your Cobo Portal Apps to Cobo Portal. For more details about publish Cobo Portal Apps, refer to [Publish the app](/developers/v2/apps/build-app#publish-the-app).

Before uploading your Cobo Portal Apps, ensure the following:

* Verify the [app manifest file](/developers/v2/apps/build-app#configure-the-manifest-file) is configured correctly.
* Log into Cobo CLI with your Cobo Portal account.
* Generate an app key if you haven't done so. For more details, refer to [Generate keys](/developers/v2/developer-tools/cobo-cli/key-management#generate-keys).
* Run the command from the project directory where the manifest file is located.

Upon successful upload, an `app_id` value will be automatically added to the app manifest file.

<Note>A Cobo Portal App can be uploaded only once. For any further updates, you will need to use the [update command](/developers/v2/developer-tools/cobo-cli/app-update).</Note>

## Usage

```shell theme={null}
cobo app upload
```

## Example

```shell theme={null}
cobo app upload
```

This command uploads a Cobo Portal App to Cobo Portal.


# Changelog
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/changelog

Stay updated with all the latest changes and additions to Cobo CLI through the changelog.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This changelog details all additions and changes to Cobo CLI.

## v0.0.5

This version was released on January 3, 2025.

This release includes the following changes:

* Cobo Portal Apps now support approval workflows. When creating a Cobo Portal App using the `cobo app init` command, you can configure these workflows in the `operation_approval_rules` field of the `manifest.json` file. For detailed instructions, refer to [Configure approval workflow](/developers/v2/apps/configure-workflow).
* Fixed some bugs.

## v0.0.4

This version was released on November 22, 2024. This is the first release of Cobo CLI.

This release includes support for the following features:

* **[API interaction](/developers/v2/developer-tools/cobo-cli/get-requests)**: Easily interact with Cobo WaaS 2.0 through [RESTful API](/developers/v2/api-references/playground) directly from your terminal.
* **[App management](/developers/v2/developer-tools/cobo-cli/app-init)**: Streamline your development process by creating applications from pre-built templates that support multiple programming languages and frameworks, with the WaaS SDK pre-integrated. Additionally, you can use Cobo CLI to build, manage, and publish [Cobo Portal Apps](/developers/v2/apps/introduction) efficiently through the command line.
* **[Multiple authentication methods](/developers/v2/developer-tools/cobo-cli/login-and-authentication)**: Utilize and test three types of authentication mechanisms: Cobo Portal account, Org Access Token, and API key.
* **[Webhook testing](/developers/v2/developer-tools/cobo-cli/listen-and-forward-events)**: Test and debug your webhook integrations locally.
* **[Real-time API monitoring](/developers/v2/developer-tools/cobo-cli/real-time-logs)**: Stream API request logs for quick debugging and monitoring.
* **[Environment switching](/developers/v2/developer-tools/cobo-cli/global-options#environment-selection-e-env)**: Seamlessly switch between the development and production environments, allowing for safe testing and development before deploying to production.
* **[API documentation lookup](/developers/v2/developer-tools/cobo-cli/api-documentation)**: Access helpful documentation for the Cobo WaaS 2.0 API, requests, responses, and their parameters directly from the command line.


# Command reference
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/cli-commands

A comprehensive guide to all commands supported by Cobo CLI for efficient usage.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## version

Use the [version](/developers/v2/developer-tools/cobo-cli/version-and-updates) command to display the current version of Cobo CLI.

```shell theme={null}
cobo version
```

## login

Use the [login](/developers/v2/developer-tools/cobo-cli/login-and-authentication) command to log in to your Cobo Portal account or acquire an Org Access Token.

```shell theme={null}
cobo login [options]
```

**Options**

* `-u`, `--user`: Log in with your Cobo Portal account (default).
* `-o`, `--org`: Acquire an Org Access Token.
* `--refresh-token`: Refresh the existing Org Access Token instead of generating a new one.

**Example**

```shell theme={null}
cobo login --org
```

## logout

Use the [logout](/developers/v2/developer-tools/cobo-cli/login-and-authentication#remove-an-access-token) commands to log out of your Cobo Portal account or remove the Org Access Token.

```shell theme={null}
cobo logout [options]
```

**Options**

* `-u`, `--user`: Log out from your Cobo Portal account.
* `-o`, `--org`: Remove the Org Access Token only.
* `-a`, `--all`: Log out from your Cobo Portal account and remove the Org Access Token (default behavior).

**Example**

```shell theme={null}
cobo logout --user
```

## auth

Use the [auth](/developers/v2/developer-tools/cobo-cli/login-and-authentication) command to set or view the current authentication method.

```shell theme={null}
cobo auth <method>
```

**Arguments**

* `method`: The authentication method to set. Possible values include `apikey`, `user`, and `org`.

**Example**

```shell theme={null}
cobo auth apikey
```

## env

Use the [env](/developers/v2/developer-tools/cobo-cli/environment-management) command to set or view the current environment.

```shell theme={null}
cobo env <environment>
```

**Arguments**

* `<environment>`: The environment to set. Possible values include `dev` and `prod`.

**Example**

```shell theme={null}
cobo env prod
```

## keys

Use the [keys](/developers/v2/developer-tools/cobo-cli/key-management) commands to generate and manage API key pairs and app key pairs.

### generate

Use the `generate` command to generate a new API or app key pair.

```shell theme={null}
cobo keys generate [options]
```

**Options**

* `--key-type <key_type>`: Specify the type of key to generate (`API` or `APP`). Default is `API`.
* `--alg <algorithm>`: Specify the key generation algorithm. Default is `ed25519`.
* `--force`: Force replacement of existing keys.

**Example**

```shell theme={null}
cobo keys generate --key-type APP --force
```

## config

Use the [config](/developers/v2/developer-tools/cobo-cli/configuration) commands to manage CLI configuration settings.

### set

Use the `set` command to set a configuration value.

```shell theme={null}
cobo config set <key> <value>
```

**Arguments**

* `key`: The key to set.
* `value`: The value to set.

**Example**

```shell theme={null}
cobo config set environment dev
```

### get

Use the `get` command to get a configuration value.

```shell theme={null}
cobo config get <key>
```

**Arguments**

* `key`: The key to get.

**Example**

```shell theme={null}
cobo config get environment
```

### list

Use the `list` command to list all configuration values.

```shell theme={null}
cobo config list
```

### delete

Use the `delete` command to delete a configuration value.

```shell theme={null}
cobo config delete <key>
```

**Arguments**

* `key`: The key to delete.

**Example**

```shell theme={null}
cobo config delete api_key
```

## app

### app init

Use the [init](/developers/v2/developer-tools/cobo-cli/app-init) command to create an application that integrates the WaaS 2.0 service.

```shell theme={null}
cobo app init [options]
```

**Options**

* `-t`, `--app-type <portal|web|mobile|automation>`: The type of WaaS application.
* `--auth <apikey|org|user>`: The authentication method that the application uses to access the WaaS 2.0 service.
* `--wallet-type <custodial-asset|custodial-web3|mpc-org-controlled|mpc-user-controlled|exchange>`: The wallet type that the application interacts with.
* `--mobile <flutter|react-native|kotlin|swift>`: The mobile development framework of the application.
* `--web <react|nextjs|vue|svelte>`: The web development framework of the application.
  <Note>Currently Cobo CLI only supports `react`.</Note>
* `--backend <fastapi|django|express|flask|spring-boot|gin|laravel|rails|nextjs>`: The backend development framework of the application.
  <Note>Currently Cobo CLI only supports `fastapi`.</Note>
* `-d`, `--directory <DIRECTORY>`: The directory in which you want to create the application project.
* `-f`, `--force`: Force overwrite the project directory if it already exists.

**Example**

```shell theme={null}
cobo app init --app-type web --auth apikey --directory my_project
```

### app upload

Use the [upload](/developers/v2/developer-tools/cobo-cli/app-upload) command to publish your Cobo Portal Apps to Cobo Portal.

```shell theme={null}
cobo app upload
```

### app update

Use the [update](/developers/v2/developer-tools/cobo-cli/app-update) command to deploy updates to a Cobo Portal App on Cobo Portal.

```shell theme={null}
cobo app update
```

### app status

Use the [status](/developers/v2/developer-tools/cobo-cli/app-status) command to check the status of Cobo Portal Apps.

```shell theme={null}
cobo app status
```

## webhook

### listen

Use the [listen](/developers/v2/developer-tools/cobo-cli/listen-and-forward-events) command to establish a WebSocket connection to the WaaS 2.0 service and stream webhook events.

```shell theme={null}
cobo webhook listen [options]
```

**Options**

* `--events <event_type>`: Filter the events by specifying event types. Possible values for event types include:
  * `wallets.transaction.created`
  * `wallets.transaction.updated`
  * `wallets.transaction.failed`
  * `wallets.transaction.succeeded`
  * `wallets.mpc.tss_request.created`
  * `wallets.mpc.tss_request.updated`
  * `wallets.mpc.tss_request.failed`
  * `wallets.mpc.tss_request.succeeded`
* `--forward <url>`: Forward received events to the specified URL.

**Example**

```shell theme={null}
cobo webhook listen --events wallets.transaction.created,wallets.transaction.updated --forward "https://your-endpoint.com/webhook"
```

### trigger

Use the [trigger](/developers/v2/developer-tools/cobo-cli/trigger-events) command to test the functionality of your webhook endpoint by triggering a test webhook event.

```shell theme={null}
cobo webhook trigger <event_type> [options]
```

**Arguments**

`<event_type>`: The webhook event type you want to trigger. Possible values include:

* `wallets.transaction.created`
* `wallets.transaction.updated`
* `wallets.transaction.failed`
* `wallets.transaction.succeeded`
* `wallets.mpc.tss_request.created`
* `wallets.mpc.tss_request.updated`
* `wallets.mpc.tss_request.failed`
* `wallets.mpc.tss_request.succeeded`

**Options**

`--override <json_string>`: Override specific fields in the event payload with the provided JSON string.

**Example**

```shell theme={null}
cobo webhook trigger wallets.transaction.updated --override '{"chain_id": "ETH", "amount": "1000000000000000000"}'
```

### events

Use the [events](/developers/v2/developer-tools/cobo-cli/event-types) command to retrieve all available webhook event types in WaaS 2.0.

```shell theme={null}
cobo webhook events
```

## API commands

### get

Use the [get](/developers/v2/developer-tools/cobo-cli/get-requests) command to make a GET request to the WaaS 2.0 service. You can also use it to retrieve a list of all available GET operations or display the description of a specified operation within the WaaS 2.0 API.

<Note>To make API requests via Cobo CLI, you need to authenticate your requests by logging in and using Org Access Tokens or API Keys as the authentication method. For more information, refer to [Authenticate with Org Access Tokens](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-org-access-tokens) and [Authenticate with API Keys](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-api-keys).</Note>

```shell theme={null}
cobo get <path> [options]
```

**Arguments**

`<path>`: The URL of the endpoint to which the GET request will be sent.

**Options**

* `-d, --describe`: Display the description of the specified GET operation, including its expected responses and error information (if any).
* `-l, --list`: List all available GET operations of the WaaS 2.0 service.

**Example**

```shell theme={null}
cobo get /wallets/11223344
```

### post

Use the [post](/developers/v2/developer-tools/cobo-cli/post-requests) command to make a POST request to the WaaS 2.0 service. You can also use it to retrieve a list of all available POST operations or display the description of a specified operation within the WaaS 2.0 API.

<Note>To make API requests via Cobo CLI, you need to authenticate your requests by logging in and using Org Access Tokens or API Keys as the authentication method. For more information, refer to [Authenticate with Org Access Tokens](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-org-access-tokens) and [Authenticate with API Keys](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-api-keys).</Note>

```shell theme={null}
cobo post <path> [options]
```

**Arguments**

`<path>`: The URL of the endpoint to which the POST request will be sent.

**Options**

* `-d, --describe`: Display the description of the specified POST operation, including its expected responses and error information (if any).
* `-l, --list`: List all available POST operations of the WaaS 2.0 service.

**Example**

```shell theme={null}
cobo post /wallets --name "My New Wallet" --wallet_type Custodial
```

### put

Use the [put](/developers/v2/developer-tools/cobo-cli/put-requests) command to make a PUT request to the WaaS 2.0 service. You can also use it to retrieve a list of all available PUT operations or display the description of a specified operation within the WaaS 2.0 API.

<Note>To make API requests via Cobo CLI, you need to authenticate your requests by logging in and using Org Access Tokens or API Keys as the authentication method. For more information, refer to [Authenticate with Org Access Tokens](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-org-access-tokens) and [Authenticate with API Keys](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-api-keys).</Note>

```shell theme={null}
cobo put <path> [options]
```

**Arguments**

`<path>`: The URL of the endpoint to which the PUT request will be sent.

**Options**

* `-d, --describe`: Display the description of the specified PUT operation, including its expected responses and error information (if any).
* `-l, --list`: List all available PUT operations of the WaaS 2.0 service.

**Example**

```shell theme={null}
cobo put /wallets/{wallet_id} --wallet_id your_wallet_id --name "Updated Wallet Name"
```

### delete

Use the [delete](/developers/v2/developer-tools/cobo-cli/delete-requests) command to make a DELETE request to the WaaS 2.0 service. You can also use it to retrieve a list of all available DELETE operations or display the description of a specified operation within the WaaS 2.0 API.

<Note>To make API requests via Cobo CLI, you need to authenticate your requests by logging in and using Org Access Tokens or API Keys as the authentication method. For more information, refer to [Authenticate with Org Access Tokens](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-org-access-tokens) and [Authenticate with API Keys](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-api-keys).</Note>

```shell theme={null}
cobo delete <path> [options]
```

**Arguments**

`<path>`: The URL of the endpoint to which the DELETE request will be sent.

**Options**

* `-d, --describe`: Display the description of the specified DELETE operation, including its expected responses and error information (if any).
* `-l, --list`: List all available DELETE operations of the WaaS 2.0 service.

**Example**

```shell theme={null}
cobo delete -l
```

## Utility commands

### logs tail

Use the [logs tail](/developers/v2/developer-tools/cobo-cli/real-time-logs) command to stream real-time logs of your API requests to the WaaS 2.0 service directly in your terminal.

```shell theme={null}
cobo logs tail [options]
```

**Options**

* `--http-method`: Filter API logs by the HTTP method, such as `POST`.
* `--request-path`: Filter API logs by the endpoint path, such as `/v2/wallets/{wallet_id}`.
* `--status-code`: Filter API logs by the HTTP status code, such as `200`.
* `--api-key`: Filter API logs by a specific API key used in requests.
* `--ip-address`: Filter API logs by the IP address from which requests were made.

**Example**

```shell theme={null}
cobo logs tail --http-method POST --status-code 404 --request-path /v2/wallets --ip-address 192.168.1.1
```

### open

Use the [open](/developers/v2/developer-tools/cobo-cli/open-browser-shortcuts) command to open various pages of Cobo Portal conveniently in your default web browser with shortcuts.

```shell theme={null}
cobo open <shortcut>
```

**Arguments**

`<shortcut>`: Shortcut used to quickly open a page of Cobo Portal. The following shortcuts are available:

* `portal`: The login page of Cobo Portal
* `dashboard`: The Dashboard page
* `wallets`: The Wallets overview page
* `custodial`: The Custodial Wallets overview page
* `mpc`: The MPC Wallets overview page
* `exchange`: The Exchange Wallets overview page
* `developer`: Developer Console
* `apps`: The Cobo Portal Apps overview page
* `pricing`: The Pricing Plans page
* `approval`: The Approvals page

**Example**

```shell theme={null}
cobo open mpc
```

### doc

Use the [doc](/developers/v2/developer-tools/cobo-cli/api-documentation) command to fetch and update the latest WaaS 2.0 OpenAPI specification.

```shell theme={null}
cobo doc <topic_or_path> [options]
```

**Arguments**

`<topic_or_path>`: Specifies the documentation topic or the API operation path. Possible values include:

* `guides`: (Default)Opens the [Introduction to WaaS 2.0](/developers/v2/guides/overview/introduction) guide.
* `api`: Opens the [API Reference](/developers/v2/api-references/playground) page.
* `sdk`: Opens the [WaaS SDKs](/developers/v2/developer-tools/quickstart-python) guide.
* `apps`: Opens the [Cobo Portal App development](/developers/v2/apps/introduction) guide.
* API endpoint paths: Displays detailed information on API operations available for the specified path such as `/wallets`.

**Options**

`-u`, `--update`: Update the OpenAPI specification for WaaS 2.0, ensuring you have the latest API definitions and documentation.

**Example**

```shell theme={null}
cobo doc /wallets/mpc/vaults
```


# Configuring Cobo CLI
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/configuration

Guide to inspect and modify Cobo CLI configurations for optimal command usage.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This guide introduces how to inspect and modify the configurations of Cobo CLI. The configurations are used by various Cobo CLI commands, including `cobo env`, `cobo auth`, and `cobo keys`.

By default, Cobo CLI stores its configurations in your home directory (`~/.cobo/config.toml`). You can override this location by using the `--config-file <path>` option. For more information about this option, see [Global options](/developers/v2/developer-tools/cobo-cli/global-options#custom-configuration-file-config-file).

## Configuration commands

### Set configuration values

To set a configuration value, use the following command:

```shell theme={null}
cobo config set <key> <value>
```

### Retrieve configuration values

To retrieve a configuration value, use the following command:

```shell theme={null}
cobo config get <key>
```

If the configuration key exists, it will display the value. Otherwise, it will inform you that the configuration was not found.

### List all configurations

To see all your current configuration settings, use the `list` subcommand:

```shell theme={null}
cobo config list
```

This will display all key-value pairs in your configuration.

### Delete configuration Values

To remove a configuration value, use the `delete` subcommand:

```shell theme={null}
cobo config delete <key>
```

## Important configurations

While you can store any custom configuration values, there are some key settings that Cobo CLI uses:

### Environment

You can set the environment using the `cobo config set environment <environment>` command:

```shell theme={null}
cobo config set environment dev
```

Cobo CLI supports two environments:

* `dev`: For development purposes
* `prod`: For production use

<Note>
  This command has the same effect as running `cobo env dev`.
</Note>

### Authentication method

You can set the authentication method using the `cobo config set auth_method <method>` command:

```shell theme={null}
cobo config set auth_method apikey
```

Cobo CLI supports three authentication methods:

* `apikey`: Authenticate with an API key.
* `user`: Authenticate with your Cobo Portal account.
* `org`: Authenticate with an Org Access Token.

<Note>
  This command has the same effect as running `cobo auth apikey`.
</Note>


# DELETE requests
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/delete-requests

Perform DELETE HTTP requests to the WaaS 2.0 service using Cobo CLI.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use the `delete` command to perform DELETE HTTP requests to a specified endpoint of the WaaS 2.0 service.

If the `path` argument is provided, the command initiates a DELETE request to that endpoint. Otherwise, it retrieves a list of all available DELETE operations or displays the description of a specified operation within the WaaS 2.0 API.

<Note>To make API requests via Cobo CLI, you need to authenticate your requests by logging in and using Org Access Tokens or API Keys as the authentication method. For more information, refer to [Authenticate with Org Access Tokens](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-org-access-tokens) and [Authenticate with API Keys](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-api-keys).</Note>

<Note>Currently there is no DELETE operation within the WaaS 2.0 API.</Note>

## Usage

```shell theme={null}
cobo delete <path> [options]
```

## Arguments

`<path>`: The URL of the endpoint to which the DELETE request will be sent.

## Options

* `-d, --describe`: Display the description of the specified DELETE operation, including its expected responses and error information (if any).
* `-l, --list`: List all available DELETE operations of the WaaS 2.0 service.

## Example

```shell theme={null}
cobo delete -l
```

This command lists all available DELETE operations of the WaaS 2.0 service.

## API Reference

For a complete list of available DELETE endpoints and their parameters, refer to the [API reference](/developers/v2/api-references).


# Environment management
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/environment-management

Switch between development and production environments with Cobo CLI.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Cobo CLI allows you to switch between the [development and production environments](/developers/v2/guides/overview/environments). This guide explains how to switch between environments effectively. Always remember to switch to the correct environment before executing commands to avoid unintended actions in the wrong environment.

<Note>
  Cobo CLI is designed for use in the development environment by default. Always exercise caution when using it in the production environment, and ensure you understand the implications of each command before execution.
</Note>

## View current environment

To check which environment is currently active, use:

```shell theme={null}
cobo env
```

This command will display the name of the currently active environment.

## Set environment

To switch to a different environment, use the following command:

```shell theme={null}
cobo env <environment>
```

Replace `<environment>` with your desired environment (`dev` or `prod`). This command will set the specified environment as the active one for subsequent CLI commands.

<Info>
  If you don't specify an environment, Cobo CLI defaults to the "development" environment.
</Info>

## Override environment for a single command

You can override the current environment for a single command by using the
global `-e` or `--env` option:

```shell theme={null}
cobo -e <environment> {command}
```

This allows you to execute a command in a specific environment without changing the overall active environment.


# List event types
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/event-types

Retrieve available webhook event types in WaaS 2.0 using Cobo CLI.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use this command to retrieve all available webhook event types in WaaS 2.0. Possible values for event types include:

* `wallets.transaction.created`
* `wallets.transaction.updated`
* `wallets.transaction.failed`
* `wallets.transaction.succeeded`
* `wallets.mpc.tss_request.created`
* `wallets.mpc.tss_request.updated`
* `wallets.mpc.tss_request.failed`
* `wallets.mpc.tss_request.succeeded`

## Usage

```shell theme={null}
cobo webhook events
```

## Example

```shell theme={null}
cobo webhook events
```

This command retrieves all available webhook event types.


# GET requests
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/get-requests

Perform GET HTTP requests to the WaaS 2.0 service using Cobo CLI.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use the `get` command to perform GET HTTP requests to a specified endpoint of the WaaS 2.0 service.

If the `path` argument is provided, the command initiates a GET request to that endpoint. Otherwise, it retrieves a list of all available GET operations or displays the description of a specified operation within the WaaS 2.0 API.

<Note>To make API requests via Cobo CLI, you need to authenticate your requests by logging in and using Org Access Tokens or API Keys as the authentication method. For more information, refer to [Authenticate with Org Access Tokens](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-org-access-tokens) and [Authenticate with API Keys](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-api-keys).</Note>

## Usage

```shell theme={null}
cobo get <path> [options]
```

## Arguments

`<path>`: The URL of the endpoint to which the GET request will be sent.

## Options

* `-d, --describe`: Display the description of the specified GET operation, including its expected responses and error information (if any). You can use this option with parameter names to retrieve specific descriptions, for example:

  ```shell theme={null}
  cobo get -d /wallets/mpc/vaults --name --vault_type
  ```

  This command displays the information about both the `name` and `vault_type` parameters for the API operation of getting the vault information.

* `-l, --list`: List all available GET operations of the WaaS 2.0 service.

## Example

### Retrieve wallet information

```shell theme={null}
cobo get /wallets/11223344
```

This command retrieves information about a specific wallet whose wallet ID is `11223344`.

### Get operation description

```shell theme={null}
cobo get /wallets -d
```

This command retrieves the description of the [Get wallet information](/developers/v2/api-references/wallets/get-wallet-information) operation.

### List all GET operations

```shell theme={null}
cobo get -l
```

This command lists all available GET operations of the WaaS 2.0 service.

## API Reference

For a complete list of available GET endpoints and their parameters, refer to the [API reference](/developers/v2/api-references).


# Global options
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/global-options

Customize Cobo CLI command behavior with global options for environment and authentication.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Cobo CLI provides several global options that can be used with any command to customize its behavior. These options allow you to control the environment, authentication method, and other settings for your CLI operations.

<Note>
  Global options should be placed before the specific command you want to run. For example, `-e prod` should come before `get /wallets`.
</Note>

## Available global options

### Environment selection (-e, --env)

The `-e` or `--env` option allows you to override the default environment for a specific command.

```shell theme={null}
cobo -e dev get /wallets
```

Possible values include:

* `dev`: Development environment
* `prod`: Production environment

If not specified, Cobo CLI will use the environment set in your configuration or default to the development environment.

### Authentication method (-a, --auth)

The `-a` or `--auth` option allows you to override the default [authentication method](/developers/v2/developer-tools/cobo-cli/login-and-authentication#manage-authentication-methods) for a specific command.

```shell theme={null}
cobo -a user get /wallets
```

Possible values include:

* `apikey`: API key
* `user`: Cobo Portal account
* `org`: Org Access Token

If not specified, Cobo CLI will use the authentication method set in your configuration or default to API key authentication.

### Debug mode (--enable-debug)

The `--enable-debug` flag enables debug mode, which provides verbose logging for troubleshooting purposes.

```shell theme={null}
cobo --enable-debug get /wallets
```

### Custom configuration file (--config-file)

The `--config-file` option allows you to specify a custom configuration file instead of the default one.

```shell theme={null}
cobo --config-file /path/to/config.toml get /wallets 
```

If not specified, Cobo CLI will use the default configuration file located in your home directory (`~/.cobo/config.toml`).

### Custom API specification file (--spec)

If you have a custom OpenAPI specification file, you can use it with Cobo CLI. This is useful for testing or working with different versions of the API.

To use a custom specification file:

```bash theme={null}
$ cobo --spec /path/to/custom_spec.yaml get /wallets -d
```

Replace /path/to/custom\_spec.yaml with the actual path to your custom specification file.

<Note>Using a custom specification file will override the default OpenAPI specification for that command only. It won’t affect other commands or future uses of Cobo CLI.</Note>

## Combining global options

You can combine multiple global options in a single command:

```shell theme={null}
cobo -e prod -a user --enable-debug get /wallets
```

This command will:

1. Use the production environment.
2. Authenticate using your Cobo Portal account.
3. Enable debug mode for verbose logging.
4. Execute the GET request to retrieve wallet information.

## Configuration precedence

The Cobo CLI follows the following order of precedence when determining which settings to use:

1. Command line options (highest priority)
2. Configuration file settings
3. Default values (lowest priority)

This allows you to easily override settings on a per-command basis without modifying your configuration files.


# Introduction to Cobo CLI
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/introduction

Learn about Cobo CLI, a tool for building, testing, and managing WaaS 2.0 integrations.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Cobo Command Line Interface (CLI) is a powerful developer tool designed to help you build, test, and manage your integration with [Cobo Wallet-as-a-Service (WaaS) 2.0](/developers/v2/guides/overview/introduction) directly from the command line.

## Key features

* **[API interaction](/developers/v2/developer-tools/cobo-cli/get-requests)**: Easily interact with Cobo WaaS 2.0 through [RESTful API](/developers/v2/api-references/playground) directly from your terminal.
* **[App management](/developers/v2/developer-tools/cobo-cli/app-init)**: Streamline your development process by creating applications from pre-built templates that support multiple programming languages and frameworks, with the WaaS SDK pre-integrated. Additionally, you can use Cobo CLI to build, manage, and publish [Cobo Portal Apps](/developers/v2/apps/introduction) efficiently through the command line.
* **[Multiple authentication methods](/developers/v2/developer-tools/cobo-cli/login-and-authentication)**: Utilize and test three types of authentication mechanisms: Cobo Portal account, Org Access Token, and API key.
* **[Webhook testing](/developers/v2/developer-tools/cobo-cli/trigger-events)**: Test and debug your webhook integrations locally.
* **[Real-time API monitoring](/developers/v2/developer-tools/cobo-cli/real-time-logs)**: Stream API request logs for quick debugging and monitoring.
* **[Environment switching](/developers/v2/developer-tools/cobo-cli/global-options#environment-selection-e-env)**: Seamlessly switch between the development and production environments, allowing for safe testing and development before deploying to production.
* **[API documentation lookup](/developers/v2/developer-tools/cobo-cli/api-documentation)**: Access helpful documentation for the Cobo WaaS 2.0 API, requests, responses, and their parameters directly from the command line.

## Use cases

Cobo CLI is particularly useful for:

* Developers integrating Cobo WaaS 2.0 into their applications.
* DevOps engineers managing Cobo resources and monitoring transactions.
* QA teams testing Cobo integrations and API responses.
* Support teams troubleshooting customer issues related to Cobo's services.

## Example usage

Here are some quick examples of how to use Cobo CLI. These examples demonstrate some of the key functionalities of Cobo CLI, including REST API interactions, application management, accessing API documentation, real-time log monitoring, and webhook event handling.

1. List all Custodial Wallets:

```shell theme={null}
cobo get /wallets --wallet_type Custodial 
```

2. Create a new application with WaaS SDK integrated using a template:

```shell theme={null}
cobo app init --app-type portal --web react --backend fastapi -d demo_project
```

3. Look up documentation for a specific API operation:

```shell theme={null}
cobo doc /wallets/{wallet_id}/utxos
```

4. Monitor real-time API request logs for debugging and troubleshooting:

```shell theme={null}
cobo logs tail --http-method GET --request-path /wallets
```

5. Trigger a webhook event:

```shell theme={null}
cobo webhook trigger wallets.transaction.updated --override '{"wallet_id": "1234567890"}'
```

6. Listen for webhook events and forward them to a local endpoint:

```shell theme={null}
cobo webhook listen --events wallets.transaction.updated --forward http://localhost:9988
```


# Key management
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/key-management

Generate and manage API and app key pairs for authentication to the WaaS 2.0 service.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This guide explains how to generate and manage API key paris and app key pairs using Cobo CLI. All keys are used for authenticating with Cobo WaaS 2.0.

## Generate keys

Use the `keys generate` command to generate a new API key pair (an API key and an API secret) or an app key pair (an app key and an app secret).

### Usage

```shell theme={null}
cobo keys generate [options]
```

### Options

* `--key-type <key_type>`: Specify the type of key to generate (`API` or `APP`). Default is `API`.
* `--alg <algorithm>`: Specify the key generation algorithm. Default is `ed25519`.
* `--force`: Force replacement of existing keys.

### Example

Generate a new API key pair:

```shell theme={null}
cobo keys generate
```

Generate a new app key pair:

```shell theme={null}
cobo keys generate --key-type APP
```

Force replacement of existing API key pair:

```shell theme={null}
cobo keys generate --force
```

## Key storage

Generated keys are securely stored in your configuration file (default: `~/.cobo/config.toml`).

<Warning>
  Never share your API secret or app secret. Keep it secure and use the API key only when registering it on Cobo Portal.
</Warning>

## Best practices

* Regularly rotate your API key pairs or app key pairs to maintain security.
* Use different keys for the development and production environments.
* Limit the permissions associated with each key to the minimum required for its intended use.
* Monitor key usage and revoke any keys that may have been compromised.


# Listen and forward events
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/listen-and-forward-events

Stream and forward webhook events from the WaaS 2.0 service using Cobo CLI.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use this command to establish a WebSocket connection to the WaaS 2.0 service and stream webhook events, as well as optionally forward them to a specified URL. You can use **Ctrl + C** to stop the event listening process.

<Note>This command is mainly intended for use in development and testing environments. For production environment, set up a proper webhook endpoint in your application as instructed in [Set up a callback or webhook endpoint](/developers/v2/guides/webhooks-callbacks/set-up-endpoint).</Note>

## Usage

```shell theme={null}
cobo webhook listen [options]
```

## Options

* `--events <event_type>`: Filter the events by specifying event types. Replace `<event_type>` with the specific event types you're interested in and separate them by commas. Possible values for event types include:

  * `wallets.transaction.created`
  * `wallets.transaction.updated`
  * `wallets.transaction.failed`
  * `wallets.transaction.succeeded`
  * `wallets.mpc.tss_request.created`
  * `wallets.mpc.tss_request.updated`
  * `wallets.mpc.tss_request.failed`
  * `wallets.mpc.tss_request.succeeded`

  <Info>You can also run the [cobo webhook events](/developers/v2/developer-tools/cobo-cli/event-types) command to get the latest list of all available event types.</Info>

* `--forward <url>`: Forward received events to the specified URL.
  <Note>When using this option, ensure that your endpoint is properly secured, especially if you're forwarding to a public URL.</Note>

## Example

```shell theme={null}
cobo webhook listen --events wallets.transaction.created,wallets.transaction.updated --forward "https://your-endpoint.com/webhook"
```

This command listens for the `wallets.transaction.created` and `wallets.transaction.updated` event types and forward the received events to the url `https://your-endpoint.com/webhook`.


# Login and authentication
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/login-and-authentication

Authenticate Cobo CLI with the WaaS 2.0 service using API keys, Org Access Tokens, or Cobo Portal accounts.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This guide explains how to authenticate your Cobo CLI to Cobo Wallet-as-a-Service (WaaS) 2.0. You'll learn about the three available authentication methods, understand their key differences, and get step-by-step instructions for implementing each approach. Choose the authentication method that best suits your security requirements and use case.

## Manage authentication methods

Cobo CLI supports the following three authentication methods:

* Log in with your Cobo Portal account. Cobo CLI will be granted the same permissions and wallet scope as your Cobo Portal account. You can use this method to manage your Cobo Portal Apps, such as creating, publishing, and updating an app.
* You can also use an API key for authentication. Cobo CLI will be granted the permissions and wallet scope configured for the API key.
* If you want to test your Cobo Portal App locally through Cobo CLI, you can use an Org Access Token for authentication. This method grants your Cobo Portal App access to an organization.

You can switch between these methods using the `auth` command:

```shell theme={null}
cobo auth <METHOD>
```

Replace `<METHOD>` with one of the following:

* `apikey`: Use the API Key to authenticate. For more details, refer to [API key and API secret](/developers/v2/guides/overview/cobo-auth#api-key-and-api-secret).
* `user`: Log in with your Cobo Portal account.
* `org`: Use the Org Access Token to authenticate. For more details, refer to [Org Access Tokens](/developers/v2/apps/org-access-tokens).

For example, to switch to the API Key authentication method, run the following command:

```shell theme={null}
cobo auth apikey
```

To view the current authentication method, run the following command:

```shell theme={null}
cobo auth
```

## Log in with your Cobo Portal account

To log in with your Cobo Portal account, run the following command:

```
cobo login --user
```

This command will initiate the user login process:

1. Cobo CLI will display a browser URL and a setup code.
2. You'll be prompted to open a browser to continue the authorization process. If you confirm, your default browser will open with the provided URL.

<img alt="Log in with your Cobo Portal account" />

3. Verify that the setup code shown in your browser matches the code displayed in your terminal. This step ensures the security of your login process.
4. After verifying that the codes match, proceed with authorization by selecting your target organization and clicking **Confirm**. This completes the login process and grants Cobo CLI access to the selected organization.

## Authenticate with Org Access Tokens

An Org Access Token allows a Cobo Portal App to access an organization's resources.

### Submit your app to Cobo

To acquire an Org Access Token, you need to create a Cobo Portal App and submit it to Cobo first:

1. Create a Cobo Portal App. Select `portal` as the app type when prompted.

   ```
   cobo app init
   ```

2. In the root directory of the app that you created, generate an app key, which is used by Cobo to authenticate a Cobo Portal App.

   ```
   cobo keys generate --key-type APP
   ```

3. [Log in with your Cobo Portal account](#log-in-with-your-cobo-portal-account). This is required before you can submit your app to Cobo. Follow the instructions on the screen to complete the authentication process.

   ```
   cobo login --user
   ```

4. Submit your app to Cobo for approval.

   ```
   cobo app upload
   ```

### Acquire an Org Access Token

After you submit your app to Cobo, you can acquire an Org Access Token by running the following command:

```
cobo login --org
```

This command will:

1. Display a browser URL and a setup code in the terminal.
2. Prompt you to open a browser to continue the authorization process. If you confirm, your default browser will open with the provided URL.

<img alt="Acquire an Org Access Token" />

3. Verify that the setup code shown in your browser matches the code displayed in your terminal. This step ensures the security of your authentication process.
4. After verifying that the codes match, proceed with authorization by granting permissions for Cobo CLI to access your organization's resources.

After submitting the authorization request, your organization's admin will need to approve it. Once approved, your Org Access Token will be saved in the `.env` file in the root directory of your project.

<Note>
  If you want to call the WaaS APIs with the Org Access Token, you need to have your app approved by Cobo first.
</Note>

### Refresh an Org Access Token

It is best practice to regularly refresh your Org Access Token to maintain security. To refresh an existing Org Access Token and update it in the `.env` file, add the `--refresh-token` flag:

```shell theme={null}
cobo login --org --refresh-token
```

## Authenticate with API keys

To use this method, you need to generate an API key and an API secret, and register the API key on [Cobo Portal](https://portal.cobo.com).

1. Generate an API key pair (an API key and an API secret) by running the following command.
   ```shell theme={null}
   cobo keys generate
   ```
2. Add the newly generated API key to Cobo Portal by following the instructions in [Register an API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key). Remember to update the API key in Cobo Portal every time you generate a new key pair.

<Info>You can quickly access the developer console by using the `cobo open developer` command. This shortcut opens your browser and takes you directly to the right page in Cobo Portal.</Info>

<Warning>
  Ensure you grant only the necessary permissions to your API key. Limiting access helps maintain the security of your account and resources.
</Warning>

Once you've added the API key to Cobo Portal and set the appropriate permissions, your Cobo CLI will be able to authenticate using this key for subsequent operations.

## Log out

To log out of Cobo CLI, use the `logout` command:

```shell theme={null}
cobo logout
```

You can specify the authentication method you want to log out from using the following options:

* `cobo logout --user`: Log out from your Cobo Portal account.
* `cobo logout --org`: Remove the Org Access Token only. You will need to acquire a new token to authenticate your CLI.
* `cobo logout --all`: Log out from your Cobo Portal account and remove the Org Access Token (this is the default behavior if no option is specified).

## Best Practices

* Keep your keys and access tokens secure and never share them with others. Use environment variables or a secure configuration file to store them.
* Regularly refresh your tokens and rotate your API keys to maintain security. Remember to update the API key in Cobo Portal every time you generate a new key pair.


# Open browser shortcuts
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/open-browser-shortcuts

Use Cobo CLI shortcuts to quickly open Cobo Portal pages in your browser.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use this command to open various pages of Cobo Portal conveniently in your default web browser with shortcuts.

<Note>Using certain shortcuts such as `dashboard`, `wallets`, `custodial`, `mpc`, and `exchange` requires login and authentication. If you're not logged in, you'll be redirected to the login page.</Note>

## Usage

```shell theme={null}
cobo open <shortcut>
```

## Arguments

`<shortcut>`: Shortcut used to quickly open a page of Cobo Portal.

The following shortcuts are available:

* `portal`: The login page of Cobo Portal
* `dashboard`: The Dashboard page
* `wallets`: The Wallets overview page
* `custodial`: The Custodial Wallets overview page
* `mpc`: The MPC Wallets overview page
* `exchange`: The Exchange Wallets overview page
* `developer`: Developer Console
* `apps`: The Cobo Portal Apps overview page
* `pricing`: The Pricing Plans page
* `approval`: The Approvals page

## Example

```shell theme={null}
cobo open mpc
```

This command opens the MPC Wallets overview page.


# POST requests
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/post-requests

Perform POST HTTP requests to the WaaS 2.0 service using Cobo CLI.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use the `post` command to perform POST HTTP requests to a specified endpoint of the WaaS 2.0 service.

If the  `path` argument is provided, the command initiates a POST request to that endpoint. Otherwise, it retrieves a list of all available POST operations or displays the description of a specified operation within the WaaS 2.0 API.

<Note>To make API requests via Cobo CLI, you need to authenticate your requests by logging in and using Org Access Tokens or API Keys as the authentication method. For more information, refer to [Authenticate with Org Access Tokens](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-org-access-tokens) and [Authenticate with API Keys](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-api-keys).</Note>

## Usage

```shell theme={null}
cobo post <path> [options]
```

## Arguments

`<path>`: The URL of the endpoint to which the POST request will be sent.

## Options

* `-d, --describe`: Display the description of the specified POST operation, including its expected responses and error information (if any). You can use this option with parameter names to retrieve specific descriptions, for example:

  ```shell theme={null}
  cobo post -d /wallets/mpc/vaults --name --vault_type
  ```

  This command displays the information about both the `name` and `vault_type` parameters for the API operation of creating a vault.
* `-l, --list`: List all available POST operations of the WaaS 2.0 service.

## Example

### Create a new wallet

```shell theme={null}
cobo post /wallets --name "My New Wallet" --wallet_type Custodial --wallet_subtype Asset
```

This command creates a new Custodial Wallet (Asset Wallet) named `My New Wallet`.

### POST operation description

```shell theme={null}
cobo post /wallets -d
```

This command retrieves the description of the [Create wallet](/developers/v2/api-references/wallets/create-wallet) operation.

### List all POST operations

```shell theme={null}
cobo post -l
```

This command lists all available POST operations of the WaaS 2.0 service.

## API Reference

For a complete list of available POST endpoints and their parameters, refer to the [API reference](/developers/v2/api-references).


# PUT requests
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/put-requests

Perform PUT HTTP requests to the WaaS 2.0 service using Cobo CLI.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use the `put` command to perform PUT HTTP requests to a specified endpoint of the WaaS 2.0 service.

If the `path` argument is provided, the command initiates a PUT request to that endpoint. Otherwise, it retrieves a list of all available PUT operations or displays the description of a specified operation within the WaaS 2.0 API.

<Note>To make API requests via Cobo CLI, you need to authenticate your requests by logging in and using Org Access Tokens or API Keys as the authentication method. For more information, refer to [Authenticate with Org Access Tokens](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-org-access-tokens) and [Authenticate with API Keys](/developers/v2/developer-tools/cobo-cli/login-and-authentication#authenticate-with-api-keys).</Note>

## Usage

```shell theme={null}
cobo put <path> [options]
```

## Arguments

`<path>`: The URL of the endpoint to which the PUT request will be sent.

## Options

* `-d, --describe`: Display the description of the specified PUT operation, including its expected responses and error information (if any). You can use this option with parameter names to retrieve specific descriptions, for example:

  ```shell theme={null}
  cobo put -d /wallets/mpc/projects/{project_id} --name
  ```

  This command displays the information about the `name` parameter for the API operation of updating the MPC project name.
* `-l, --list`: List all available PUT operations of the WaaS 2.0 service.

## Example

### Update wallet information

```shell theme={null}
cobo put /wallets/11223344 --name "Updated Wallet Name"
```

This command updates the name of a specific wallet with wallet ID of `11223344` to `Updated Wallet Name`.

### Get operation description

```shell theme={null}
cobo put /wallets/{wallet_id} -d
```

This command retrieves the description of the [Update wallet](/developers/v2/api-references/wallets/update-wallet) operation.

### List all PUT operations

```shell theme={null}
cobo put -l
```

This command lists all available PUT operations of the WaaS 2.0 service.

## API Reference

For a complete list of available PUT endpoints and their parameters, refer to the [API reference](/developers/v2/api-references).


# Quick start guide
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/quick-start-guide

Get started with Cobo CLI installation, authentication, configuration, and basic commands.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This guide walks you through getting started with Cobo CLI. You'll learn how to:

* Install Cobo CLI
* Log in and authenticate with your Cobo Portal account
* Configure your environment for optimal use
* Learn basic CLI commands for wallet management, transaction handling, and other key operations

<Note>
  Cobo CLI is designed for use in the development environment by default. Always exercise caution when using it in the production environment, and ensure you understand the implications of each command before execution.
</Note>

## Prerequisites

* Follow the instructions in Cobo Portal's [Set up your account and organization](https://manuals.cobo.com/en/portal/quick-start-guide) to set up your Cobo Portal account and create your organization. If an organization has already been set up, ask your organization admin to invite you to join the organization.
* Basic knowledge of the command line interface

## Install Cobo CLI

### System requirements

Cobo CLI is supported on most operating systems. Ensure your system meets the following requirements:

* macOS (10.14 Mojave or later)
* Windows 10 or later
* Linux (most distributions supported)

### Install Cobo CLI

Choose the installation method that best suits your operating system:

#### Use pip

You can install Cobo CLI using pip, which works on all supported operating systems:

```shell theme={null}
pip install cobo-cli
```

Ensure that you have Python 3.9 or newer installed.

#### Use Homebrew

You can install Cobo CLI on macOS using Homebrew:

```shell theme={null}
brew install cobo-cli
```

### Verify the installation

To verify that Cobo CLI has been installed correctly, open a new terminal and run the following command:

```shell theme={null}
cobo version
```

## Log in and authenticate

After installing Cobo CLI, you need to authenticate your Cobo CLI to Cobo WaaS 2.0. You can choose one of the [three authentication methods](/developers/v2/developer-tools/cobo-cli/login-and-authentication) to authenticate. As an example, this guide will show you how to authenticate with your Cobo Portal account:

1. Switch to use your Cobo Portal account to authenticate:

   ```
   cobo auth user
   ```
2. Run the following command to initiate the user login process:

   ```
   cobo login --user
   ```
3. You'll be prompted to open a browser to continue the authorization process. Complete the authorization process in your browser, granting the necessary permissions for Cobo CLI to access your organization.

## Configure your environment

Configure your environment for development or production use. We always recommend starting with the development environment:

```
cobo env dev
```

For more information about environments, see [Development and production environments](/developers/v2/guides/overview/environments).

## Send your first request

Now you have successfully installed and configured Cobo CLI. It is time to explore what you can do with Cobo CLI.

### List all Custodial Wallets:

If you already have one or more Custodial Wallets, you can list all your Custodial Wallets by running the following command:

```shell theme={null}
cobo get /wallets --wallet_type Custodial 
```

### Look up API documentation

If you have questions about a specific API operation, you can look up the API documentation by running the following command:

```shell theme={null}
cobo doc /wallets
```

### Create a new application

Create a new application using a template, with the WaaS SDK integrated:

```shell theme={null}
cobo app init
```


# View real-time logs
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/real-time-logs

Stream real-time API request logs in your terminal for monitoring and troubleshooting.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use this command to stream real-time logs of your API requests to the WaaS 2.0 service directly in your terminal.

The command provides detailed information about each API request, including the request method, endpoint, status code, and more, enabling you to monitor and troubleshoot interactions with the WaaS 2.0 service in real time.

<Note>The `cobo logs tail` command requires proper authentication and permissions. Ensure that you are logged in and have the necessary access permissions to view the API logs.</Note>

## Usage

```shell theme={null}
cobo logs tail [options]
```

## Options

* `--http-method`: Filter API logs by the HTTP method, such as `POST`.
* `--request-path`: Filter API logs by the endpoint path, such as `/v2/wallets/{wallet_id}`.
* `--status-code`: Filter API logs by the HTTP status code, such as `200`.
* `--api-key`: Filter API logs by a specific API key used in requests.
* `--ip-address`: Filter API logs by the IP address from which requests were made.

## Example

```shell theme={null}
cobo logs tail --http-method POST --status-code 404 --request-path /v2/wallets --ip-address 192.168.1.1
```

This command fetches the API logs with HTTP method `POST`, status code `404`, and requests to `/v2/wallets` endpoint from a specific IP `192.168.1.1` .


# Trigger webhook events
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/trigger-events

Test your webhook endpoint by triggering test events with Cobo CLI.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Use this command to test the functionality of your webhook endpoint by triggering a test webhook event. The test event will be sent to all the webhook endpoints you have registered on Cobo Portal. You can optionally provide the `override_data` option to customize the payload.

## Usage

```shell theme={null}
cobo webhook trigger <event_type> [options]
```

## Arguments

`<event_type>`: The webhook event type you want to trigger. Possible values include:

* `wallets.transaction.created`
* `wallets.transaction.updated`
* `wallets.transaction.failed`
* `wallets.transaction.succeeded`
* `wallets.mpc.tss_request.created`
* `wallets.mpc.tss_request.updated`
* `wallets.mpc.tss_request.failed`
* `wallets.mpc.tss_request.succeeded`

<Info>You can also run the [cobo webhook events](/developers/v2/developer-tools/cobo-cli/event-types) command to get the latest list of all available event types.</Info>

## Options

`--override <json_string>`: Override specific fields in the event payload with the provided JSON string.

## Example

This command triggers a `wallets.transaction.updated` event with the specified `chain_id` and `amount` values:

```shell theme={null}
cobo webhook trigger wallets.transaction.updated --override '{"chain_id": "ETH", "amount": "1000000000000000000"}'
```

## Best Practices

* **Test all event types**: Trigger events for all the webhook types your application is subscribed to, ensuring your system can handle each type correctly.
* **Use realistic data**: When overriding event data, try to use realistic values that match your production scenarios.
* **Test error handling**: Trigger events with edge case data to ensure your webhook consumer can handle unexpected scenarios.
* **Verify webhook delivery**: After triggering an event, check your webhook endpoint logs to confirm that the event was received and processed correctly.


# Version and updates
Source: https://cobo.com/developers/v2/developer-tools/cobo-cli/version-and-updates

Learn how to check and update your Cobo CLI version for the latest features and improvements.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

This guide explains how to check and manage your Cobo CLI version. You'll learn how to verify which version you're currently running and how to update to the latest release to access new features and improvements.

## Check current version

To display the current version of Cobo CLI, use the following command:

```shell theme={null}
cobo version
```

Example output:

```shell theme={null}
Cobo CLI version: 0.1.0
```

## Update Cobo CLI

To ensure you have access to the latest features and bug fixes, it's important to keep your Cobo CLI up to date. The update process depends on how you initially installed the tool.

If you installed Cobo CLI using pip, you can update it with the following command:

```shell theme={null}
pip install --upgrade cobo-cli
```

If you installed Cobo CLI using Homebrew on macOS, you can update it with these commands:

```shell theme={null}
brew upgrade cobo-cli
```

After updating, verify the new version:

```shell theme={null}
cobo version
```


# Get testnet coins
Source: https://cobo.com/developers/v2/developer-tools/get-testnet-coins

Learn how to obtain testnet coins for testing your integration with the WaaS 2.0 API.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

To test your integration with the WaaS 2.0 API, you can use Sepolia (ETH testnet) and Bitcoin testnet environments. This guide explains how to obtain testnet coins from reliable sources.

## Sepolia testnet (SETH)

Use Sepolia testnet for testing Ethereum-based transactions. Monitor your transactions using:

* **Explorer**: [Etherscan](https://sepolia.etherscan.io/)

### Obtain SETH from faucets

Get SETH from these reliable faucet services:

* [QuickNode Sepolia Faucet](https://faucet.quicknode.com/drip)
* [Alchemy Sepolia Faucet](https://sepoliafaucet.com/)
* [Grabteeth](https://grabteeth.xyz/)
* [PoW Faucet](https://sepolia-faucet.pk910.de/)

## Bitcoin testnet (XTN)

Use Bitcoin testnet for testing BTC transactions. Monitor your transactions using:

* **Explorer**: [BlockCypher](https://live.blockcypher.com/btc-testnet/)

### Obtain XTN from faucets

Get XTN from these reliable faucet services:

* [Bitaps Bitcoin Testnet Faucet](https://tbtc.bitaps.com/)
* [Bitcoin Testnet Faucet](https://bitcoinfaucet.uo1.net/)
* [Coinfaucet](https://coinfaucet.eu/en/btc-testnet/)
* [Cryptopump](https://cryptopump.info/)

## Best practices

* Keep your testnet addresses separate from production addresses
* Request only the amount you need for testing
* Release unused testnet coins back to faucets when possible


# Get started with Go SDK
Source: https://cobo.com/developers/v2/developer-tools/quickstart-go

Learn to integrate, configure, and use the Go SDK with code samples for seamless app development.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## Overview

This guide introduces how to get started with using the Cobo WaaS 2.0 Go SDK, which allows you to integrate the WaaS service into your existing application using the Go programming language.

To learn more about the initial setup steps necessary for utilizing the WaaS API, see [Send your first request](/developers/v2/guides/get-started/get-started-with-waas).

You can go to [GitHub](https://github.com/CoboGlobal/cobo-waas2-go-sdk/) to access the source code of the SDK.

## Prerequisites

* You have installed Go 1.18 or newer.
* Follow the instructions in [Set up your account and organization](https://manuals.cobo.com/en/portal/quick-start-guide) to set up your Cobo account and create your organization. If an organization has already been set up, ask your organization admin to invite you to join the organization.
* You have [generated an API key and an API secret](/developers/v2/guides/overview/cobo-auth#generate-an-api-key-and-an-api-secret), and [registered the API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key) on Cobo Portal.

## Install the SDK

1. Create a Go project if you haven't.

2. In the `go.mod` file of your project, add the following line:

   ```go theme={null}
   require github.com/CoboGlobal/cobo-waas2-go-sdk {VERSION}
   ```

   <Note>Replace \{VERSION} with the lastest version number, for example, `v1.2.0`. Obtain the latest version number from the [GitHub repository](https://github.com/CoboGlobal/cobo-waas2-go-sdk/tags).</Note>

3. Run the `go mod tidy` command in a terminal or in your IDE to install the dependencies.

4. In your `main.go` file, import the WaaS SDK as follows:

   ```go theme={null}
   import (
       ...
       coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
       ...
   )
   ```

## Configure API key and HTTP host

In the main function in your `main.go` file, configure the HTTP host by selecting the environment and provide your API secret.
The following code snippet shows the configuration for the development environment.

```go theme={null}
// Select the environment that you use and comment out the other line of code
ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
// ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.ProdEnv)
ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
    // Replace `<YOUR_API_SECRET>` with your API secret.
    Secret: "<YOUR_API_SECRET>",
})
```

## Sample code

For operation-specific documentation and sample code, see the [docs](https://github.com/CoboGlobal/cobo-waas2-go-api/tree/master/docs) folder in the WaaS SDK GitHub repository.

### List supported chains

```go theme={null}
package main

import (
	"context"
	"encoding/json"
	"fmt"
	"os"

	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
)

func main() {

	// Specify the wallet type as Custodial Wallet.
	walletType := coboWaas2.WalletType("Custodial")
	// walletType, err := coboWaas2.NewWalletTypeFromValue("Custodial")

	// Specify the wallet sub-type as Asset Wallet.
	walletSubtype := coboWaas2.WalletSubtype("Asset")
	// walletSubType, err := coboWaas2.NewWalletSubtypeFromValue("Asset")

	// Use pagination parameters if needed
	limit := int32(10)
	before := ""
	after := ""

	configuration := coboWaas2.NewConfiguration()
	apiClient := coboWaas2.NewAPIClient(configuration)
	ctx := context.Background()
	// Select the environment that you use and comment out the other line of code.
	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
	// ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.ProdEnv)
	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
		// Replace `<YOUR_API_SECRET>` with your own API secret.
		Secret: "<YOUR_API_SECRET>",
	})
	// Call the List supported chains operation.
	req := apiClient.WalletsAPI.ListSupportedChains(ctx).WalletType(walletType).WalletSubtype(walletSubtype)
	if limit > 0 {
		req = req.Limit(limit)
	}
	if before != "" {
		req = req.Before(before)
	}
	if after != "" {
		req = req.After(after)
	}
	resp, r, err := req.Execute()
	if err != nil {
		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.ListSupportedChains``: %v\n", err)
		if apiErr, ok := err.(*coboWaas2.GenericOpenAPIError); ok {
			fmt.Fprintf(os.Stderr, "Error response: %s\n", string(apiErr.Body()))
		}
		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
	}
	// Handle response from `ListSupportedChains`.
	respJson, _ := json.MarshalIndent(resp, "", " ")
	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.ListSupportedChains`: \n%s", string(respJson))
}
```

### Create a wallet

```go theme={null}
package main

import (
	"context"
	"encoding/json"
	"fmt"
	"os"

	coboWaas2 "github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2"
	"github.com/CoboGlobal/cobo-waas2-go-sdk/cobo_waas2/crypto"
)

func main() {
	// Specify the wallet type of the wallet to be created as Custodial Wallet.
	walletType, err := coboWaas2.NewWalletTypeFromValue("Custodial")
	if err != nil {
		fmt.Fprintf(os.Stderr, "Error when new `WalletType``: %v\n", err)
		return
	}
      // Specify the wallet sub-type of the wallet to be created as Asset Wallet.
	walletSubType, err := coboWaas2.NewWalletSubtypeFromValue("Asset")
	if err != nil {
		fmt.Fprintf(os.Stderr, "Error when new `WalletSubType``: %v\n", err)
		return
	}
	createWalletParams := coboWaas2.CreateWalletParams{
		CreateCustodialWalletParams: coboWaas2.NewCreateCustodialWalletParams(
            // Specify the name of the wallet to be created.
			"My WaaS 2.0 Wallet for doc test",
			*walletType,
			*walletSubType,
		)} 

	configuration := coboWaas2.NewConfiguration()
	apiClient := coboWaas2.NewAPIClient(configuration)
	ctx := context.Background()
	// Select the environment tha you use and comment out the other line of code.
	ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.DevEnv)
	// ctx = context.WithValue(ctx, coboWaas2.ContextEnv, coboWaas2.ProdEnv)
	ctx = context.WithValue(ctx, coboWaas2.ContextPortalSigner, crypto.Ed25519Signer{
        // Replace `<YOUR_API_SECRET>` with your own API secret.
		Secret: "<YOUR_API_SECRET>",
	})
	// Call the Create wallet operation.
	resp, r, err := apiClient.WalletsAPI.CreateWallet(ctx).CreateWalletParams(createWalletParams).Execute()
	if err != nil {
		fmt.Fprintf(os.Stderr, "Error when calling `WalletsAPI.CreateWallet``: %v\n", err)
		if apiErr, ok := err.(*coboWaas2.GenericOpenAPIError); ok {
			fmt.Fprintf(os.Stderr, "Error response: %s\n", string(apiErr.Body()))
		}
		fmt.Fprintf(os.Stderr, "Full HTTP response: %v\n", r)
		return
	}
	// Handle response from `CreateWallet`.
	respJson, _ := json.MarshalIndent(resp.GetActualInstance(), "", " ")
	fmt.Fprintf(os.Stdout, "Response from `WalletsAPI.CreateWallet`: \n%s", string(respJson))
}
```


# Get started with Java SDK
Source: https://cobo.com/developers/v2/developer-tools/quickstart-java

Learn to integrate, configure, and use the Java SDK with code samples for seamless app development.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## Overview

This guide introduces how to get started with using the Cobo WaaS 2.0 Java SDK, which allows you to integrate the WaaS service into your existing application using the Java programming language.

To learn more about the initial setup steps necessary for utilizing the WaaS API, see [Send your first request](/developers/v2/guides/get-started/get-started-with-waas).

You can go to [GitHub](https://github.com/CoboGlobal/cobo-waas2-java-sdk/) to access the source code of the SDK.

## Prerequisites

* Install Java 1.8 or newer

* Install Maven 3.8.3 or newer / Gradle 7.2 or newer

* Follow the instructions in [Set up your account and organization](https://manuals.cobo.com/en/portal/quick-start-guide) to set up your Cobo account and create your organization. If an organization has already been set up, ask your organization admin to invite you to join the organization.

* You have [generated an API key and an API secret](/developers/v2/guides/overview/cobo-auth#generate-an-api-key-and-an-api-secret), and [registered the API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key) on Cobo Portal.

## Add dependency

For Maven users, add the dependency to your project's POM:

```
<dependency>
  <groupId>com.cobo.waas2</groupId>
  <artifactId>cobo-waas2</artifactId>
  <version>{VERSION}</version>
  <scope>compile</scope>
</dependency>
```

For Gradle users, add the dependency to your project's build file:

```
  repositories {
    mavenCentral()     // Fetch the dependency from Maven Central
  }

  dependencies {
     implementation "com.cobo.waas2:cobo-waas2:{VERSION}"
  }
```

<Note>Replace \{VERSION} with the lastest version number, for example, `1.2.0`. Obtain the latest version number from the [GitHub repository](https://github.com/CoboGlobal/cobo-waas2-java-sdk/tags).</Note>

## Configure API key and HTTP host

1. Set the API secret.

```java theme={null}
ApiClient defaultClient = Configuration.getDefaultApiClient();
defaultClient.setPrivKey("<YOUR_API_SECRET_IN_HEX>");
```

2. Select which [environment](/developers/v2/guides/overview/environments) you want to use. The SDK uses the production environment by default.

```java theme={null}
// Select the development environment
defaultClient.setEnv(Env.DEV);

// Select the production environment
defaultClient.setEnv(Env.PROD);
```

## Code samples

For operation-specific documentation and sample code, see the [docs](https://github.com/CoboGlobal/cobo-waas2-java-sdk/tree/master/docs) folder in the WaaS SDK GitHub repository.

### List supported chains

```java theme={null}
// Import classes 
import com.cobo.waas2.ApiClient;
import com.cobo.waas2.ApiException;
import com.cobo.waas2.Configuration;
import com.cobo.waas2.Env;
import com.cobo.waas2.model.*;
import com.cobo.waas2.api.WalletsApi;

public class Example {
  public static void main(String[] args) {
    ApiClient defaultClient = Configuration.getDefaultApiClient();
    // Use the development environment 
    defaultClient.setEnv(Env.DEV);
    // Set the API secret
    defaultClient.setPrivKey("<YOUR_API_SECRET_IN_HEX>");
    WalletsApi apiInstance = new WalletsApi();
    WalletType walletType = WalletType.fromValue("Custodial");
    WalletSubtype walletSubtype = WalletSubtype.fromValue("Asset");
    String chainIds = "";
    Integer limit = 10;
    String before = "";
    String after = "";
    try {
      // List supported chains
      ListSupportedChains200Response result = apiInstance.listSupportedChains(walletType, walletSubtype, chainIds, limit, before, after);
      System.out.println(result);
    } catch (ApiException e) {
      System.err.println("Exception when calling WalletsApi#listSupportedChains");
      System.err.println("Status code: " + e.getCode());
      System.err.println("Reason: " + e.getResponseBody());
      System.err.println("Response headers: " + e.getResponseHeaders());
      e.printStackTrace();
    }
  }
}
```

### Create a wallet

```java theme={null}
// Import classes 

import com.cobo.waas2.ApiClient;
import com.cobo.waas2.ApiException;
import com.cobo.waas2.Configuration;
import com.cobo.waas2.Env;
import com.cobo.waas2.model.*;
import com.cobo.waas2.api.WalletsApi;

public class Example {
    public static void main(String[] args) {
        ApiClient defaultClient = Configuration.getDefaultApiClient();
        // Use the development environment 
        defaultClient.setEnv(Env.DEV);
        // Set the API secret
        defaultClient.setPrivKey("<YOUR_API_SECRET_IN_HEX>");
        WalletsApi apiInstance = new WalletsApi();
        CreateWalletParams createWalletParams = new CreateWalletParams(
                new CreateCustodialWalletParams()
                        .name("Example Wallet")
                        .walletType(WalletType.CUSTODIAL)
                        .walletSubtype(WalletSubtype.ASSET)
        );
        try {
            // Create a Custodial Wallet
            CreatedWalletInfo result = apiInstance.createWallet(createWalletParams);
            System.out.println(result);
        } catch (ApiException e) {
            System.err.println("Exception when calling WalletsApi#createWallet");
            System.err.println("Status code: " + e.getCode());
            System.err.println("Reason: " + e.getResponseBody());
            System.err.println("Response headers: " + e.getResponseHeaders());
            e.printStackTrace();
        }
    }
}
```


# Get started with JavaScript SDK
Source: https://cobo.com/developers/v2/developer-tools/quickstart-javascript

Learn to integrate, configure, and use the JavaScript  SDK with code samples for seamless app development.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## Overview

This guide introduces how to get started with using the Cobo WaaS 2.0 JavaScript SDK, which allows you to integrate the WaaS service into your existing application using the JavaScript programming language.

To learn more about the initial setup steps necessary for utilizing the WaaS API, see [Send your first request](/developers/v2/guides/get-started/get-started-with-waas).

You can go to [GitHub](https://github.com/CoboGlobal/cobo-waas2-js-sdk/) to access the source code of the SDK.

## Prerequisites

* Install Node.js and NPM.

* Follow the instructions in [Set up your account and organization](https://manuals.cobo.com/en/portal/quick-start-guide) to set up your Cobo account and create your organization. If an organization has already been set up, ask your organization admin to invite you to join the organization.

* You have [generated an API key and an API secret](/developers/v2/guides/overview/cobo-auth#generate-an-api-key-and-an-api-secret), and [registered the API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key) on Cobo Portal.

## Create a project and install the SDK

1. Create a project directory and initialize NPM:

```bash theme={null}
mkdir waas2-js && cd waas2-js
npm init -y
```

2. Install the SDK:

```bash theme={null}
npm install @cobo/cobo-waas2 --save
```

The directory structure after installation is as follows:

```pgsql theme={null}
waas2-js/
├─ node_modules/
├─ package.json
├─ package-lock.json
└─ (to be created later) index.js
```

<Tip> If your project already has <code>package.json</code> and <code>package-lock.json</code>, you can directly copy them to the root directory and run <code>npm install</code> to pull dependencies.</Tip>

3. Create a file <code>index.js</code> in the root directory and paste the following code into it.

The directory structure after installation is as follows:

```pgsql theme={null}
waas2-js/
├─ node_modules/
├─ package.json
├─ package-lock.json
└─ (to be created later) index.js
```

<Tip> If your project already has <code>package.json</code> and <code>package-lock.json</code>, you can directly copy them to the root directory and run <code>npm install</code> to pull dependencies.</Tip>

3. Create a file <code>index.js</code> in the root directory and paste the following code into it.

## Configure API key and HTTP host

1. Set the API secret.

```javascript theme={null}
// Initialize the default API client
const apiClient = CoboWaas2.ApiClient.instance
// Set the API secret
apiClient.setPrivateKey("<YOUR_API_SECRET_IN_HEX>");
```

2. Select which [environment](/developers/v2/guides/overview/environments) you want to use.

```javascript theme={null}
// Select the development environment
apiClient.setEnv(CoboWaas2.Env.DEV);

// Select the production environment
apiClient.setEnv(CoboWaas2.Env.PROD);
```

## Code sample

For operation-specific documentation and sample code, see the [docs](https://github.com/CoboGlobal/cobo-waas2-js-sdk/tree/master/docs) folder in the WaaS SDK GitHub repository.

### List supported chains

```javascript theme={null}
const CoboWaas2 = require("@cobo/cobo-waas2");
// Initialize the API client
const apiClient = CoboWaas2.ApiClient.instance;
// Set the environment (development: Env.DEV, production: Env.PROD)
apiClient.setEnv(CoboWaas2.Env.DEV);
// Configure API Secret – replace <YOUR_PRIVATE_KEY> with your API Secret
apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
// Create a WalletsApi instance
const apiInstance = new CoboWaas2.WalletsApi();
// Define query parameters
const opts = {
  wallet_type: "Custodial",      // Wallet type: Custodial wallet
  wallet_subtype: "Asset",       // Wallet subtype: Asset wallet
  chain_ids: "BTC,ETH",          // Chain IDs to query: BTC, ETH
  limit: 10,                     // Limit the number of results to 10 entries
  before: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGmk1", // For pagination, optional
  after: "RqeEoTkgKG5rpzqYzg2Hd3szmPoj2cE7w5jWwShz3C1vyGSAk",  // For pagination, optional
};
// Call the API to list supported chains
apiInstance.listSupportedChains(opts).then(
  (data) => {
    console.log("API called successfully. Returned data: " + data);
  },
  (error) => {
    console.error(error);
  },
);
```

Example response is as follows:

```javascript theme={null}
API called successfully. Returned data: {
 "data": [
   {
     "chain_id": "BTC",
     "symbol": "Bitcoin",
     "icon_url": "https://d.cobo.com/public/logos/btc%403x.png",
     "explorer_tx_url": "https://mempool.space/tx/{txn_id}",
     "explorer_address_url": "https://mempool.space/address/{address}",
     "require_memo": false,
     "confirming_threshold": 4
   },
   {
     "chain_id": "ETH",
     "symbol": "Ethereum",
     "icon_url": "https://d.cobo.com/public/logos/eth%403x.png",
     "explorer_tx_url": "https://etherscan.io/tx/{txn_id}",
     "explorer_address_url": "https://etherscan.io/address/{address}",
     "require_memo": false,
     "confirming_threshold": 64
   }
 ],
 "pagination": {
   "before": "",
   "after": "",
   "total_count": 2
 }
}
```

### Create a wallet

```javascript theme={null}
const CoboWaas2 = require("@cobo/cobo-waas2");
// Initialize the API client
const apiClient = CoboWaas2.ApiClient.instance;
// Set the environment (development: Env.DEV, production: Env.PROD)
apiClient.setEnv(CoboWaas2.Env.DEV);
// Configure API Secret – replace <YOUR_PRIVATE_KEY> with your API Secret
apiClient.setPrivateKey("<YOUR_PRIVATE_KEY>");
// Create a WalletsApi instance
const apiInstance = new CoboWaas2.WalletsApi();
// Define parameters for wallet creation
const opts = {
  CreateWalletParams: CoboWaas2.CreateWalletParams.constructFromObject({
    name: "My WaaS 2.0 Wallet", // Wallet name
    wallet_type: "Custodial",   // Wallet type: Custodial Wallets
    wallet_subtype: "Asset",    // Wallet subtype: Asset Wallets
  }),
};
// Call the API to create a wallet
apiInstance.createWallet(opts).then(
  (data) => {
    console.log("API called successfully. Returned data: " + data);
  },
  (error) => {
    console.error(error);
  },
);
```


# Get started with Python SDK
Source: https://cobo.com/developers/v2/developer-tools/quickstart-python

Learn to integrate, configure, and use the Python SDK with code samples for seamless app development.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

## Overview

This guide introduces how to get started with using the Cobo WaaS 2.0 Python SDK, which allows you to integrate the WaaS service into your existing application using the Python programming language.

To learn more about the initial setup steps necessary for utilizing the WaaS API, see [Send your first request](/developers/v2/guides/get-started/get-started-with-waas).

You can go to [GitHub](https://github.com/CoboGlobal/cobo-waas2-python-sdk/) to access the source code of the SDK.

## Prerequisites

* You have installed Python 3.7 or newer.
* Follow the instructions in [Set up your account and organization](https://manuals.cobo.com/en/portal/quick-start-guide) to set up your Cobo account and create your organization. If an organization has already been set up, ask your organization admin to invite you to join the organization.
* You have [generated an API key and an API secret](/developers/v2/guides/overview/cobo-auth#generate-an-api-key-and-an-api-secret), and [registered the API key](https://manuals.cobo.com/en/portal/developer-console/create-api-key) on Cobo Portal.

## Install the SDK

1. Install the SDK using the pip install command.
   Open a terminal window and run the following command:

   ```shell theme={null}
   pip install cobo-waas2=={VERSION}
   ```

<Note>Replace \{VERSION} with the lastest version number, for example, `1.2.0`. Obtain the latest version number from the [GitHub repository](https://github.com/CoboGlobal/cobo-waas2-python-sdk/tags).</Note>

2. Import the package in your project files as follows:

   ```python theme={null}
   import cobo_waas2
   ```

## Configure API key and HTTP host

You can refer to the [configuration.py file](https://github.com/CoboGlobal/cobo-waas2-python-api/blob/master/cobo_waas2/configuration.py) in the SDK repository for all supported configuration parameters.

```python theme={null}
configuration = cobo_waas2.Configuration(

  # Replace `<YOUR_API_SECRET>` with your API secret.
  api_private_key="<YOUR_API_SECRET>",

  # To use the development environment, set the host to `https://api.dev.cobo.com/v2`.
  # To use the production environment, set the host to `https://api.cobo.com/v2`.
  host="https://api.dev.cobo.com/v2"

)
```

## Code samples

For operation-specific documentation and sample code, see the [docs](https://github.com/CoboGlobal/cobo-waas2-python-api/tree/master/docs) folder in the WaaS SDK GitHub repository.

### List supported chains

```python theme={null}
import cobo_waas2
from pprint import pprint

configuration = cobo_waas2.Configuration(
   # Replace `<YOUR_API_SECRET>` with your API secret
   api_private_key="<YOUR_API_SECRET>",
   # Use the development environment
   host="https://api.dev.cobo.com/v2"
)

# Enter a context with an instance of the API client
with cobo_waas2.ApiClient(configuration) as api_client:
   # Create an instance of the API class
   api_instance = cobo_waas2.WalletsApi(api_client)
   try:
       # List all supported chains
       api_response = api_instance.list_supported_chains()
       print("The response of WalletsApi->list_supported_chains:\n")
       pprint(api_response)
   except Exception as e:
       print("Exception when calling WalletsApi->list_supported_chains: %s\n" % e)
```

### Create a wallet

```python theme={null}
import cobo_waas2
from pprint import pprint

from cobo_waas2 import CreateCustodialWalletParams, WalletType, WalletSubtype

configuration = cobo_waas2.Configuration(
    # Replace `<YOUR_API_SECRET>` with your API secret
    api_private_key="<YOUR_API_SECRET>",
    # Use the development environment
    host="https://api.dev.cobo.com/v2"
)
# Enter a context with an instance of the API client
with cobo_waas2.ApiClient(configuration) as api_client:
    # Create an instance of the API class
    api_instance = cobo_waas2.WalletsApi(api_client)
    create_wallet_params = cobo_waas2.CreateWalletParams(
        actual_instance=CreateCustodialWalletParams(
            name="New Custodial Wallet",
            wallet_type=WalletType.CUSTODIAL,
            wallet_subtype=WalletSubtype.ASSET,
        ),
    )
    try:
        # Create a Custodial Wallet
        api_response = api_instance.create_wallet(create_wallet_params=create_wallet_params)
        print("The response of WalletsApi->create_wallet:\n")
        pprint(api_response)
    except Exception as e:
        print("Exception when calling WalletsApi->create_wallet: %s\n" % e)
```


# Get started with UCW SDK (iOS)
Source: https://cobo.com/developers/v2/developer-tools/quickstart-ucw-ios

Learn to integrate, install, and implement MPC Wallets (User-Controlled Wallets) with detailed code samples.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<Tip>Some links in this document may not be functional until all relevant documentation for MPC Wallets (User-Controlled Wallets) has been published.</Tip>

## Overview

This guide introduces how to get started with using the [UCW SDK (iOS)](/developers/v2/developer-tools/ucw-sdk/initialize-secrets/initialize-secrets), which is required to [implement your own MPC Wallets (User-Controlled Wallets)](/developers/v2/guides/mpc-wallets/get-started-ucw), and allows you to integrate the UCW SDK into your [Client App](/developers/v2/guides/mpc-wallets/get-started-ucw#technical-architecture) to interact with the [Cobo TSS Relay](/developers/v2/guides/mpc-wallets/get-started-ucw#technical-architecture).

You can go to [GitHub](https://github.com/CoboGlobal/cobo-ucw-sdk-ios) to access the source code of the [UCW SDK](/developers/v2/developer-tools/ucw-sdk/initialize-secrets/initialize-secrets).

## Install the UCW SDK

You can install the UCW SDK as a dependency in a [Swift package](https://developer.apple.com/documentation/xcode/swift-packages) or an Xcode project.

<Tabs>
  <Tab title="Swift package">
    To install UCW SDK as a dependency in a Swift package, follow these instructions:

    1. Create a Swift package with Xcode, see [Creating a standalone Swift package with Xcode](https://developer.apple.com/documentation/xcode/creating-a-standalone-swift-package-with-xcode).

    2. Add UCW SDK to the `dependencies` in your `Package.swift` file:

       ```swift theme={null}
       dependencies: [
           .package(url: "https://github.com/CoboGlobal/cobo-ucw-sdk-ios")
       ]

       ```

    3. Add the following to the `target`:
       ```swift theme={null}
       targets: [
           .target(
               name: "<project_name>",
               dependencies: ["UCWSDK"]
           )
       ]

       ```

    4. In the source file where you want to use UCW SDK, add the following:

       ```swift theme={null}
       import UCWSDK
       ```
  </Tab>

  <Tab title="Xcode project">
    To install UCW SDK as a dependency in an Xcode project, follow these instructions:

    1. Set up your [Client App](/developers/v2/guides/mpc-wallets/get-started-ucw#technical-architecture)'s application development environment with Xcode, see [Creating an Xcode project for an app](https://developer.apple.com/documentation/xcode/creating-an-xcode-project-for-an-app).
    2. Once your Xcode project is set up, click **File** > **Add Package Dependency** in Xcode and enter the repository URL: `https://github.com/CoboGlobal/cobo-ucw-sdk-ios`. For more details, see [Adding package dependencies to your app](https://developer.apple.com/documentation/xcode/adding-package-dependencies-to-your-app).
    3. In the source file where you want to use UCW SDK, add the following:

       ```swift theme={null}
       import UCWSDK
       ```
  </Tab>
</Tabs>

## Code samples

This section demonstrates the implementation of steps directly involving the UCW SDK when creating a Main Group. For a complete guide on creating a Main Group or implementing your own MPC Wallets (User-Controlled Wallets), see [Get started with MPC Wallets (User-Controlled Wallets)](/developers/v2/guides/mpc-wallets/get-started-ucw).

For operation-specific documentation and sample code, see [UCW SDK operations on Developer Hub](/developers/v2/developer-tools/ucw-sdk/initialize-secrets/initialize-secrets).

<Steps>
  <Step title="Initialize Secrets">
    This step corresponds to Step 1 under **Complete the initial setup** > **Initialize UCW SDK** in [Get started with MPC Wallets (User-Controlled Wallets)](/developers/v2/guides/mpc-wallets/get-started-ucw). See [Initialize Secrets](/developers/v2/developer-tools/ucw-sdk/initialize-secrets/initialize-secrets) for the documentation of this operation.

    ```swift theme={null}
    let secrets = "secrets.db"
    let passphrase = "d3hxNyoiAP@Lm!D7Qpo_hghdpgyc_r39"

    Task {
       do {
           let nodeID = try await initializeSecrets(secretsFile: secrets, passphrase: passphrase)
           print(" TSS Node ID: \(nodeID)")
       } catch {
           print("Error: \(error)")
       }
    }

    ```
  </Step>

  <Step title="Create UCW SDK">
    This step corresponds to Step 1 under **Complete the initial setup** > **Create a Main Group** in [Get started with MPC Wallets (User-Controlled Wallets)](/developers/v2/guides/mpc-wallets/get-started-ucw). See [Create UCW](/developers/v2/developer-tools/ucw-sdk/ucw-class/create-ucw) for the documentation of this operation.

    ```swift theme={null}
    let secrets = "secrets.db"
    let passphrase = "d3hxNyoiAP@Lm!D7Qpo_hghdpgyc_r39"
    let sdkConfig = SDKConfig(env: Env.development, timeout: 30, debug: true)
    var sdkInstance: UCW?
    var connCode: ConnCode = .CodeUnknown
    var connMessage: String? = ""

    do {
        sdkInstance = try UCW(config: sdkConfig, secretsFile: secrets, passphrase: passphrase) { code, message in
            connCode = code
            connMessage = message
            print("Connection Code: \(connCode), Message: \(connMessage ?? "No message")")
        }
    } catch {
        print("Error: \(error)")
    }

    ```
  </Step>

  <Step title="Get TSS Node ID">
    This step corresponds to Step 3 under **Complete the initial setup** > **Create a Main Group** in [Get started with MPC Wallets (User-Controlled Wallets)](/developers/v2/guides/mpc-wallets/get-started-ucw). See [Get TSS Node ID](/developers/v2/developer-tools/ucw-sdk/ucwpublic-class/get-tss-node-id) for the documentation of this operation.

    ```swift theme={null}
    do {
        if let nodeID = try sdkInstance?.getTSSNodeID() {
            print("TSS Node ID: \(nodeID)")
        } else {
            print("Failed to get TSS Node ID")
        }
    } catch {
        print("Error: \(error)")
    }

    ```
  </Step>

  <Step title="Get TSS requests">
    This step corresponds to Step 22 under **Complete the initial setup** > **Create a Main Group** in [Get started with MPC Wallets (User-Controlled Wallets)](/developers/v2/guides/mpc-wallets/get-started-ucw). See [Get TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests) for the documentation of this operation.

    ```swift theme={null}
    let tssRequestIDs = ["tss_request_id_01"]
    Task {
        do {
            if let requests = try await sdkInstance?.getTSSRequests(tssRequestIDs: tssRequestIDs) {
                for request in requests {
                    print("\(request)\n")
                }
            } else {
                print("Get no TSS request")
            }
        } catch {
            print("Error: \(error)")
        }
    }

    ```
  </Step>

  <Step title="Approve TSS requests">
    This step corresponds to Step 27 under **Complete the initial setup** > **Create a Main Group** in [Get started with MPC Wallets (User-Controlled Wallets)](/developers/v2/guides/mpc-wallets/get-started-ucw). See [Approve TSS requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/approve-tss-requests) for the documentation of this operation.

    ```swift theme={null}
    let tssRequestIDs = ["tss_request_id_01"]
    do {
        try sdkInstance?.approveTSSRequests(tssRequestIDs: tssRequestIDs)
    } catch {
        print("Error: \(error)")
    }

    ```
  </Step>

  <Step title="Get TSS requests">
    This step corresponds to Step 30 under **Complete the initial setup** > **Create a Main Group** in [Get started with MPC Wallets (User-Controlled Wallets)](/developers/v2/guides/mpc-wallets/get-started-ucw). See [Get TSS Requests](/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests) for the documentation of this operation.

    ```swift theme={null}
    let tssRequestIDs = ["tss_request_id_01"]
    Task {
        do {
            if let requests = try await sdkInstance?.getTSSRequests(tssRequestIDs: tssRequestIDs) {
                for request in requests {
                    print("\(request)\n")
                }
            } else {
                print("Get no TSS request")
            }
        } catch {
            print("Error: \(error)")
        }
    }

    ```
  </Step>
</Steps>


# Initialize Secrets
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/initialize-secrets/initialize-secrets

This operation initializes a passphrase-encrypted Secrets file that contains a unique TSS Node ID.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<Info>A Secrets file contains all essential information about the TSS Node, including TSS Node ID and key shares.</Info>

<CodeGroup>
  ```Swift iOS theme={null}
  public func initializeSecrets(secretsFile: String, passphrase: String) async throws -> String
  ```

  ```Dart Flutter theme={null}
  Future<String> initializeSecrets(String secretsFile, String passphrase) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let secrets = "secrets.db"
  let passphrase = "d3hxNyoiAP@Lm!D7Qpo_hghdpgyc_r39"

  Task {
      do {
          let tssNodeID = try await initializeSecrets(secretsFile: secrets, passphrase: passphrase)
          print("TSS Node ID: \(tssNodeID)")
      } catch {
          print("Error: \(error)")
      }
  }
  ```

  ```Dart Flutter theme={null}
  const String secrets = "secrets.db";
  const String passphrase = "d3hxNyoiAP@Lm!D7Qpo_hghdpgyc_r39";

  try {
      final tssNodeID = await initializeSecrets(secrets, passphrase);
      print("TSS Node ID: $tssNodeID");
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string">
  The complete file name, including its extension, for the new Secrets file.
</ParamField>

<ParamField type="string">
  The passphrase for encrypting the Secrets file, with a minimum length of 16 characters.
</ParamField>

## Response

<ResponseField name="tssNodeID" type="string">
  The TSS Node ID associated with the Secrets file.
  For example, `coboJTKRVEWHgmigeE8FB2FDpN6nadUwXkUdsRZbhyFAq8bDV`.
</ResponseField>


# Get UCW SDK information
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/other-apis/get-sdk-info

This operation retrieves detailed information about the UCW SDK.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func getSDKInfo() throws -> SDKInfo
  ```

  ```Dart Flutter theme={null}
  Future<SDKInfo> getSDKInfo() async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  do {
      let sdkInfo = try getSDKInfo()
      print("\(sdkInfo)")
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  try {
      final sdkInfo = await getSDKInfo();
      print("$sdkInfo");
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Response

<ResponseField name="sdkInfo" type="object">
  Detailed information about the UCW SDK.

  <Expandable title="child attributes">
    <ResponseField name="version" type="string">
      The version of the UCW SDK.
    </ResponseField>
  </Expandable>
</ResponseField>


# Import Secrets
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/other-apis/import-secrets

This operation imports the JSON data of Secrets created with the [Export Secrets](https://www.cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/export-secrets) operation. The imported file will then be converted into a new passphrase-encrypted Secrets file, and TSS Node ID within the Secrets file will be returned.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func importSecrets(jsonRecoverySecrets: String, exportPassphrase: String, newSecretsFile: String, newPassphrase: String) throws -> String
  ```

  ```Dart Flutter theme={null}
  Future<String> importSecrets(String jsonRecoverySecrets, String exportPassphrase, String newSecretsFile, String newPassphrase) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let jsonRecoverySecrets = "{}" // exported jsonRecoverySecrets
  let exportPassphrase = "wZdcycVuexvmgt7aMkaeA_2_ioCKrw!B" 
  let newSecretsFile = "secrets.db" 
  let newPassphrase = "d3hxNyoiAP@Lm!D7Qpo_hghdpgyc_r39" 

  do {
      let tssNodeID = try importSecrets(
          jsonRecoverySecrets: jsonRecoverySecrets,
          exportPassphrase: exportPassphrase,
          newSecretsFile: newSecretsFile,
          newPassphrase: newPassphrase
      )
      print("TSS Node ID: \(tssNodeID)")
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  const String jsonRecoverySecrets = "{}"; // exported jsonRecoverySecrets
  const String exportPassphrase = "wZdcycVuexvmgt7aMkaeA_2_ioCKrw!B";
  const String newSecretsFile = "secrets.db";
  const String newPassphrase = "d3hxNyoiAP@Lm!D7Qpo_hghdpgyc_r39";

  try {
      final tssNodeID = await importSecrets(
          jsonRecoverySecrets: jsonRecoverySecrets,
          exportPassphrase: exportPassphrase,
          newSecretsFile: newSecretsFile,
          newPassphrase: newPassphrase
      );
      print("TSS Node ID: $tssNodeID");
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string">
  The passphrase-encrypted JSON data of Secrets, created by the [Export Secrets](https://www.cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/export-secrets) operations.
</ParamField>

<ParamField type="string">
  The passphrase used to decrypt the imported JSON data of Secrets.
</ParamField>

<ParamField type="string">
  The file path where the new Secrets will be stored.
</ParamField>

<ParamField type="string">
  A passphrase for encrypting the new Secrets. It must be at least 16 characters long.
</ParamField>

## Response

<ResponseField name="tssNodeID" type="string">
  The TSS Node ID of the newly created Secrets.
</ResponseField>


# Set logger
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/other-apis/set-logger

This operation enables activity logging for the UCW SDK.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func setLogger(completion: @escaping (String?, String?) -> Void)
  ```

  ```Dart Flutter theme={null}
  Future<void> setLogger(Function(String level, String message)? logCallback) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  setLogger { level, message in
      print("Log Level: \(level), Log Message: \(message)")
  }
  ```

  ```Dart Flutter theme={null}
  await setLogger((level, message) {
      print("Log Level: $level, Log Message: $message");
  });
  ```
</RequestExample>

## Parameters

<ParamField type="function">
  A callback function that receives log level and log message parameters to monitor the logger activity.

  <Expandable title="child attributes">
    <ParamField type="string">
      The log level. Possible values include:

      * `panic`: The log level is Panic.
      * `fatal`: The log level is Fatal.
      * `error`: The log level is Error.
      * `warn`: The log level is Warning.
      * `info`: The log level is Info.
      * `debug`: The log level is Debug.
    </ParamField>

    <ParamField type="string">
      The log message.
    </ParamField>
  </Expandable>
</ParamField>


# Approve transactions
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/approve-transactions

This operation approves the specified transactions.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func approveTransactions(transactionIDs: [String]) throws
  ```

  ```Dart Flutter theme={null}
  Future<void> approveTransactions(List<String> transactionIDs) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let transactionIDs = ["transaction_id_01"]

  do {
      try sdkInstance?.approveTransactions(transactionIDs: transactionIDs)
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  final List<String> transactionIDs = ["transaction_id_01"];

  try {
      await sdkInstance?.approveTransactions(transactionIDs: transactionIDs);
  } catch (error) {
       print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string[]">
  The list containing the IDs of the transactions to be approved.
</ParamField>


# Approve TSS requests
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/approve-tss-requests

This operation approves the specified TSS requests.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func approveTSSRequests(tssRequestIDs: [String]) throws
  ```

  ```Dart Flutter theme={null}
  Future<void> approveTSSRequests(List<String> tssRequestIDs) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let tssRequestIDs = ["tss_request_id_01"]

  do {
      try sdkInstance?.approveTSSRequests(tssRequestIDs: tssRequestIDs)
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  final List<String> tssRequestIDs = ["tss_request_id_01"];

  try {
      await sdkInstance?.approveTSSRequests(tssRequestIDs: tssRequestIDs);
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string[]">
  The list containing the IDs of the TSS requests to be approved.
</ParamField>


# Create UCW class
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/create-ucw

This operation creates an instance of the UCW class, decrypts the Secrets file, establishes a connection with the Cobo server, and optionally registers a callback endpoint to monitor the connection status.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<Info>The UCW class enables you to receive and approve TSS requests and transactions. Additionally, it allows you to export key shares for backing up or restoring the private keys.</Info>

<Info>The UCW class inherits from the UCWPublic class.</Info>

<CodeGroup>
  ```Swift iOS theme={null}
  public init(config: SDKConfig, secretsFile: String, passphrase: String, connCallback: @escaping(ConnCode, String?) -> Void = { _, _ in }) throws
  ```

  ```Dart Flutter theme={null}
  static Future<UCW> create({required SDKConfig config, required String secretsFile, required String passphrase, Function(ConnCode connCode, String connMessage)? connCallback}) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let secrets = "secrets.db"
  let passphrase = "d3hxNyoiAP@Lm!D7Qpo_hghdpgyc_r39"
  let sdkConfig = SDKConfig(env: Env.development, timeout: 30, debug: true)
  var sdkInstance: UCW?
  var connCode: ConnCode = .unknown
  var connMessage: String? = ""

  do {
      sdkInstance = try UCW(config: sdkConfig, secretsFile: secrets, passphrase: passphrase) { code, message in
          connCode = code
          connMessage = message
          print("Connection Code: \(connCode), Message: \(connMessage ?? "No message")")
      }
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  const String secrets = "secrets.db";
  const String passphrase = "d3hxNyoiAP@Lm!D7Qpo_hghdpgyc_r39";

  final sdkConfig = SDKConfig(
      env: Env.development,
      timeout: 30,
      debug: true
  );

  UCW? sdkInstance;
  ConnCode connCode = ConnCode.unknown;
  String? connMessage = "";

  try {
      sdkInstance = await UCW.create(
          config: sdkConfig, 
          secretsFile: secrets, 
          passphrase: passphrase,
          connCallback: (code, message) async {
              connCode = code;
              connMessage = message;
              print("Connection Code: $connCode, Message: ${connMessage ?? 'No message'}");
          }
      );
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="object">
  The configuration settings for the UCW SDK.

  <Expandable title="child attributes">
    <ParamField type="enum<string>">
      The environment type. Possible values include:

      * `development`: The operation establishes a connection with the Cobo server's development environment.
      * `production`: The operation establishes a connection with the Cobo server's production environment.
    </ParamField>

    <ParamField type="int32">
      The timeout duration for obtaining TSS requests and transactions, in seconds.
    </ParamField>

    <ParamField type="boolean">
      Whether the debug mode is enabled, which includes outputting debug-level logs.

      * `true`: The debug mode is enabled.

      * `false`: The debug mode is disabled.
    </ParamField>
  </Expandable>
</ParamField>

<ParamField type="string">
  The complete file name, including its extension, for the Secrets file that needs decryption.
</ParamField>

<ParamField type="string">
  The passphrase for decrypting the Secrets file.
</ParamField>

<ParamField type="function">
  An optional callback function to monitor connection status.

  <Expandable title="child attributes">
    <ParamField type="enum<int32>">
      The connection status code. Possible values include:

      * `1300`: Connected.
      * `1301`: Disconnected.
      * `1302`: Connection closed.
      * `1310`: Connection error.
      * `1311`: URL parse error.
      * `1320`: Connection refused.
      * `1321`: Connection failed.
      * `1350`: Proxy error.
      * `1351`: Proxy parse error.
    </ParamField>

    <ParamField type="string">
      The message associated with the `connCode`.
    </ParamField>
  </Expandable>
</ParamField>


# Destroy UCW class
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/destroy-ucw

This operation destroys an instance of the UCW class.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  deinit{}
  ```

  ```Dart Flutter theme={null}
  void dispose() async
  ```
</CodeGroup>


# Export recovery key shares
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/export-recovery-key-shares

This operation exports the specified key shares as a passphrase-encrypted JSON data, which can later be used with the [Import recovery key share](https://www.cobo.com/developers/v2/developer-tools/ucw-sdk/ucwrecoverkey-class/import-recovery-key-share) and [Recover private keys](https://www.cobo.com/developers/v2/developer-tools/ucw-sdk/ucwrecoverkey-class/recover-private-keys) operations to recover the private keys.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func exportRecoveryKeyShares(tssKeyShareGroupIDs: [String], exportPassphrase: String) throws -> String
  ```

  ```Dart Flutter theme={null}
  Future<String> exportRecoveryKeyShares(List<String> tssKeyShareGroupIDs, String exportPassphrase) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let tssKeyShareGroupIDs = ["gjRIvhmnDfpcGrzjOABE"]
  let exportPassphrase = "wZdcycVuexvmgt7aMkaeA_2_ioCKrw!B"

  do {
      if let jsonRecoverySecrets = try sdkInstance?.exportRecoveryKeyShares(tssKeyShareGroupIDs: tssKeyShareGroupIDs, exportPassphrase: exportPassphrase) {
          print("\(jsonRecoverySecrets)\n")
      } else {
          print("Failed to export recovery key shares")
      }
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  final List<String> tssKeyShareGroupIDs = ["gjRIvhmnDfpcGrzjOABE"];
  const String exportPassphrase = "wZdcycVuexvmgt7aMkaeA_2_ioCKrw!B";

  try {
      final jsonRecoverySecrets = await sdkInstance?.exportRecoveryKeyShares(
          tssKeyShareGroupIDs: tssKeyShareGroupIDs,
          exportPassphrase: exportPassphrase
      );
      print("$jsonRecoverySecrets\n");
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string[]">
  The list of TSS key share group IDs.
</ParamField>

<ParamField type="string">
  The passphrase used to encrypt the exported JSON data of recovery key shares. Must be at least 16 characters long.
</ParamField>

## Response

<ResponseField name="jsonRecoverySecrets" type="string">
  The exported passphrase-encrypted JSON data of the specified recovery key shares.
</ResponseField>


# Export Secrets
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/export-secrets

This operation exports the Secrets file as a passphrase-encrypted JSON data of TSS Node. You can then use the [Import Secrets](https://www.cobo.com/developers/v2/developer-tools/ucw-sdk/other-apis/import-secrets) operation to restore the Secrets file.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<Info>A Secrets file contains all essential information about the TSS Node, including TSS Node ID and key shares.</Info>

<CodeGroup>
  ```Swift iOS theme={null}
  public func exportSecrets(exportPassphrase: String) throws -> String
  ```

  ```Dart Flutter theme={null}
  Future<String> exportSecrets(String exportPassphrase) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let exportPassphrase = "wZdcycVuexvmgt7aMkaeA_2_ioCKrw!B"

  do {
      if let jsonRecoverySecrets = try sdkInstance?.exportSecrets(exportPassphrase: exportPassphrase) {
          print("\(jsonRecoverySecrets)\n")
      } else {
          print("Failed to export Secrets")
      }
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  const String exportPassphrase = "wZdcycVuexvmgt7aMkaeA_2_ioCKrw!B";

  try {
      final jsonRecoverySecrets = await sdkInstance?.exportSecrets(
          exportPassphrase: exportPassphrase
      );
      print("$jsonRecoverySecrets\n");
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string">
  The passphrase used to encrypt the exported JSON data of TSS Nodes. Must be at least 16 characters long.
</ParamField>

## Response

<ResponseField name="jsonRecoverySecrets" type="string">
  The exported passphrase-encrypted JSON data of Secrets, which includes the TSS Node ID and all recovery key shares.
</ResponseField>


# Get connection status
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/get-connection-status

This operation retrieves the connection status with the Cobo server.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func getConnStatus() -> (ConnCode, String?)
  ```

  ```Dart Flutter theme={null}
  ConnStatus? getConnStatus()
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  if let (connCode, connMessage) = sdkInstance?.getConnStatus() {
      print("Connection Code: \(connCode), Message: \(connMessage ?? "No message")")
  } else {
      print("Failed to get connection status")
  }
  ```

  ```Dart Flutter theme={null}
  final connStatus = sdkInstance?.getConnStatus();
  if (connStatus != null) {
      print('Connection Code: ${connStatus.connCode}, ${connStatus.connMessage}');
  } else {
      print('Failed to get connection status');
  }
  ```
</RequestExample>

## Response

<ResponseField name="connCode" type="enum<int32>">
  The connection status code. Possible values include:

  * `1300`: Connected.
  * `1301`: Disconnected.
  * `1302`: Connection closed.
  * `1310`: Connection error.
  * `1311`: URL parse error.
  * `1320`: Connection refused.
  * `1321`: Connection failed.
  * `1350`: Proxy error.
  * `1351`: Proxy parse error.
</ResponseField>

<ResponseField name="connMessage" type="string">
  The message associated with the `connCode`.
</ResponseField>


# Get transactions
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/get-transactions

This operation retrieves the specified transactions.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func getTransactions(transactionIDs: [String]) async throws -> [Transaction]
  ```

  ```Dart Flutter theme={null}
  Future<List<Transaction>> getTransactions(List<String> transactionIDs) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let transactionIDs = ["transaction_id_01"]

  Task {
      do {
          if let transactions = try await sdkInstance?.getTransactions(transactionIDs: transactionIDs) {
              for transaction in transactions {
                  print("\(transaction)\n")
              }
          } else {
              print("No transactions found")
          }
      } catch {
          print("Error: \(error)")
      }
  }
  ```

  ```Dart Flutter theme={null}
  final List<String> transactionIDs = ["transaction_id_01"];

  try {
      final transactions = await sdkInstance?.getTransactions(transactionIDs: transactionIDs);
      for (final transaction in transactions) {
          print("$transaction\n");
      }
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string[]">
  The list containing the IDs of the transactions to be retrieved.
</ParamField>

## Response

<ResponseField name="transactions" type="object[]">
  The list of retrieved transactions.

  <Expandable title="child attributes">
    <Snippet />
  </Expandable>
</ResponseField>


# Get TSS requests
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/get-tss-requests

This operation retrieves the specified TSS requests.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func getTSSRequests(tssRequestIDs: [String]) async throws -> [TSSRequest]
  ```

  ```Dart Flutter theme={null}
  Future<List<TSSRequest>> getTSSRequests(List<String> tssRequestIDs) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let tssRequestIDs = ["tss_request_id_01"]

  Task {
      do {
          if let requests = try await sdkInstance?.getTSSRequests(tssRequestIDs: tssRequestIDs) {
              for request in requests {
                  print("\(request)\n")
              }
          } else {
              print("No TSS requests found")
          }
      } catch {
          print("Error: \(error)")
      }
  }
  ```

  ```Dart Flutter theme={null}
  final List<String> tssRequestIDs = ["tss_request_id_01"];

  try {
      final requests = await sdkInstance?.getTSSRequests(tssRequestIDs: tssRequestIDs);
      for (final request in requests) {
          print("$request\n");
      }
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string[]">
  The list of IDs for the TSS requests you want to retrieve.
</ParamField>

## Response

<ResponseField name="tssRequests" type="object[]">
  The list of retrieved TSS requests.

  <Expandable title="child attributes">
    <Snippet />
  </Expandable>
</ResponseField>


# List pending transactions
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/list-pending-transactions

This operation retrieves a list of all pending transactions.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func listPendingTransactions() async throws -> [Transaction]
  ```

  ```Dart Flutter theme={null}
  Future<List<Transaction>> listPendingTransactions() async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  Task {
      do {
          if let transactions = try await sdkInstance?.listPendingTransactions() {
              for transaction in transactions {
                  print("\(transaction)\n")
              }
          } else {
              print("No pending transactions found")
          }
      } catch {
          print("Error: \(error)")
      }
  }
  ```

  ```Dart Flutter theme={null}
  try {
      final transactions = await sdkInstance?.listPendingTransactions();
      for (final transaction in transactions) {
          print("$transaction\n");
      }
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Response

<ResponseField name="transactions" type="object[]">
  The list of pending transactions.

  <Expandable title="child attributes">
    <Snippet />
  </Expandable>
</ResponseField>


# List pending TSS requests
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/list-pending-tss-requests

This operation retrieves a list of pending TSS requests.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func listPendingTSSRequests() async throws -> [TSSRequest]
  ```

  ```Dart Flutter theme={null}
  Future<List<TSSRequest>> listPendingTSSRequests() async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  Task {
      do {
          if let requests = try await sdkInstance?.listPendingTSSRequests() {
              for request in requests {
                  print("\(request)\n")
              }
          } else {
              print("No pending TSS requests found")
          }
      } catch {
          print("Error: \(error)")
      }
  }
  ```

  ```Dart Flutter theme={null}
  try {
      final requests = await sdkInstance?.listPendingTSSRequests();
      for (final request in requests) {
          print("$request\n");
      }
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Response

<ResponseField name="tssRequests" type="object[]">
  The list of pending TSS requests.

  <Expandable title="child attributes">
    <Snippet />
  </Expandable>
</ResponseField>


# Reject transactions
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/reject-transactions

This operation rejects the specified transactions and provides reason for the rejection.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func rejectTransactions(transactionIDs: [String], reason: String) throws
  ```

  ```Dart Flutter theme={null}
  Future<void> rejectTransactions(List<String> transactionIDs, String reason) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let transactionIDs = ["transaction_id_01"]
  let reason = "Insufficient funds"

  do {
      try sdkInstance?.rejectTransactions(transactionIDs: transactionIDs, reason: reason)
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  final List<String> transactionIDs = ["transaction_id_01"];
  const String reason = "Insufficient funds";

  try {
      await sdkInstance?.rejectTransactions(
          transactionIDs: transactionIDs,
          reason: reason
      );
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string[]">
  The list containing the IDs of the transactions to be rejected.
</ParamField>

<ParamField type="string">
  The detailed explanation for why the transactions are being rejected.
</ParamField>


# Reject TSS requests
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/reject-tss-requests

This operation rejects the specified TSS requests and provides reason for the rejection.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func rejectTSSRequests(tssRequestIDs: [String], reason: String) throws
  ```

  ```Dart Flutter theme={null}
  Future<void> rejectTSSRequests(List<String> tssRequestIDs, String reason) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let tssRequestIDs = ["tss_request_id_01"]
  let reason = "The TSS request does not meet the required criteria."

  do {
      try sdkInstance?.rejectTSSRequests(tssRequestIDs: tssRequestIDs, reason: reason)
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  final List<String> tssRequestIDs = ["tss_request_id_01"];
  const String reason = "The TSS request does not meet the required criteria.";

  try {
      await sdkInstance?.rejectTSSRequests(
          tssRequestIDs: tssRequestIDs, 
          reason: reason
      );
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string[]">
  The list containing the IDs of the TSS requests to be rejected.
</ParamField>

<ParamField type="string">
  A detailed explanation for why the TSS requests are being rejected.
</ParamField>


# Create UCWPublic class
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucwpublic-class/create-ucw-public

This operation creates an instance of the UCWPublic class.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<Info>The UCWPublic class allows you to retrieve the TSS Node ID and TSS key share groups without requiring a passphrase.</Info>

<CodeGroup>
  ```Swift iOS theme={null}
  public init(secretsFile: String) throws
  ```

  ```Dart Flutter theme={null}
  static Future<UCWPublic> create({required String secretsFile}) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let secrets = "secrets.db"
  var sdkInstance: UCWPublic?

  do {
      sdkInstance = try UCWPublic(secretsFile: secrets)
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  const String secrets = "secrets.db";
  UCWPublic? sdkInstance;

  try {
      sdkInstance = await UCWPublic.create(secretsFile: secrets);
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string">
  The complete file name, including its extension, for the Secrets file that needs decryption. The Secrets file was generated by the [Initialize Secrets](https://www.cobo.com/developers/v2/developer-tools/ucw-sdk/initialize-secrets/initialize-secrets) operation and provides the necessary information that allows the UCWPublic class to retrieve the TSS Node ID and TSS key share groups.
</ParamField>


# Destroy UCWPublic class
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucwpublic-class/destroy-ucw-public

This operation destroys an instance of the UCWPublic class.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  deinit{}
  ```

  ```Dart Flutter theme={null}
  void dispose() async
  ```
</CodeGroup>


# Get TSS key share groups
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucwpublic-class/get-tss-key-share-groups

This operation retrieves detailed information about the specified TSS key share groups.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func getTSSKeyShareGroups(tssKeyShareGroupIDs: [String]) throws -> [TSSKeyShareGroup]
  ```

  ```Dart Flutter theme={null}
  Future<List<TSSKeyShareGroup>> getTSSKeyShareGroups(List<String> tssKeyShareGroupIDs) async 
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let tssKeyShareGroupIDs = ["gjRIvhmnDfpcGrzjOABE"]

  do {
      if let groups = try sdkInstance?.getTSSKeyShareGroups(tssKeyShareGroupIDs: tssKeyShareGroupIDs) {
          for group in groups {
              print("\(group)\n")
          }
      } else {
          print("No TSS key share groups found")
      }
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  final List<String> tssKeyShareGroupIDs = ["gjRIvhmnDfpcGrzjOABE"];

  try {
      final groups = await sdkInstance?.getTSSKeyShareGroups(tssKeyShareGroupIDs: tssKeyShareGroupIDs);
      for (final group in groups) {
          print("$group\n");
      }
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string[]">
  The list of IDs for the TSS key share groups to be retrieved.
</ParamField>

## Response

<ResponseField name="tssKeyShareGroups" type="object[]">
  The list of retrieved TSS key share groups.

  <Expandable title="child attributes">
    <Snippet />
  </Expandable>
</ResponseField>


# Get TSS Node ID
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucwpublic-class/get-tss-node-id

This operation retrieves the TSS Node ID.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func getTSSNodeID() throws -> String
  ```

  ```Dart Flutter theme={null}
  Future<String> getTSSNodeID() async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  do {
      if let tssNodeID = try sdkInstance?.getTSSNodeID() {
          print("TSS Node ID: \(tssNodeID)")
      } else {
          print("Failed to retrieve the TSS Node ID")
      }
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  try {
      final tssNodeID = await sdkInstance?.getTSSNodeID();
      print("TSS Node ID: $tssNodeID");
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Response

<ResponseField name="tssNodeID" type="string">
  The retrieved TSS Node ID.
  For example, `coboJTKRVEWHgmigeE8FB2FDpN6nadUwXkUdsRZbhyFAq8bDV`.
</ResponseField>


# List active TSS key share groups
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucwpublic-class/list-active-tss-key-share-groups

This operation retrieves a list of all active TSS key share groups.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<Info>An active TSS key share group is one that has been created and has already completed its associated [TSS request](https://www.cobo.com/developers/v2/api-references/wallets--mpc-wallets/create-tss-request).</Info>

<CodeGroup>
  ```Swift iOS theme={null}
  public func listTSSKeyShareGroups()  throws -> [TSSKeyShareGroup]
  ```

  ```Dart Flutter theme={null}
  Future<List<TSSKeyShareGroup>> listTSSKeyShareGroups() async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  do {
      if let groups = try sdkInstance?.listTSSKeyShareGroups() {
          for group in groups {
              print("\(group)\n")
          }
      } else {
          print("Get no TSS key share group")
      }
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  try {
      final groups = await sdkInstance?.listTSSKeyShareGroups();
      for (final group in groups) {
          print("$group\n");
      }
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Response

<ResponseField name="tssKeyShareGroups" type="object[]">
  The list of active TSS key share groups.

  <Expandable title="child attributes">
    <Snippet />
  </Expandable>
</ResponseField>


# Create UCWRecoverKey class
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucwrecoverkey-class/create-ucw-recover-key

This operation creates an instance of the UCWRecoverKey class.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<Info>The UCWRecoverKey class allows you to import multiple recovery key shares to recover the private keys.</Info>

<CodeGroup>
  ```Swift iOS theme={null}
  public init(tssKeyShareGroupID: String)
  ```

  ```Dart Flutter theme={null}
  UCWRecoverKey({required this.tssKeyShareGroupID});
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let tssKeyShareGroupID = "gjRIvhmnDfpcGrzjOABE"
  var recoverKey: UCWRecoverKey?

  do {
      recoverKey = try UCWRecoverKey(tssKeyShareGroupID: tssKeyShareGroupID)
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  const String tssKeyShareGroupID = "gjRIvhmnDfpcGrzjOABE";
  UCWRecoverKey? recoverKey;

  try {
      recoverKey = UCWRecoverKey(tssKeyShareGroupID: tssKeyShareGroupID);
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string">
  The ID of the TSS key share group used to recover the private key.
</ParamField>


# Destroy UCWRecoverKey class
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucwrecoverkey-class/destroy-ucw-recover-key

This operation destroys an instance of the UCWRecoverKey class and clears the recovery key shares that have already been imported into memory.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  deinit{}
  ```

  ```Dart Flutter theme={null}
  void dispose();
  ```
</CodeGroup>


# Import recovery key share
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucwrecoverkey-class/import-recovery-key-share

This operation imports and decrypts the JSON data of recovery key shares, created by the [Export recovery key shares](https://www.cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/export-recovery-key-shares) or [Export Secrets](https://www.cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/export-secrets) operations. To meet the threshold requirement of [the Threshold Signature Scheme (TSS) specified in your User-Controlled Wallets](https://manuals.cobo.com/en/portal/mpc-wallets/ucw/project-management#overview), you must call this operation the required number of times to import enough recovery key shares.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func importRecoveryKeyShare(jsonRecoverySecrets: String, exportPassphrase: String) throws
  ```

  ```Dart Flutter theme={null}
  Future<void> importRecoveryKeyShare(String jsonRecoverySecrets, String exportPassphrase) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let jsonRecoverySecrets = "{}" // exported jsonRecoverySecrets
  let exportPassphrase = "wZdcycVuexvmgt7aMkaeA_2_ioCKrw!B"

  do {
      try recoverKey?.importRecoveryKeyShare(jsonRecoverySecrets: jsonRecoverySecrets, exportPassphrase: exportPassphrase)
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  const String jsonRecoverySecrets = "{}"; // exported jsonRecoverySecrets
  const String exportPassphrase = "wZdcycVuexvmgt7aMkaeA_2_ioCKrw!B";

  try {
      await recoverKey?.importRecoveryKeyShare(
          jsonRecoverySecrets: jsonRecoverySecrets,
          exportPassphrase: exportPassphrase
      );
  } catch (error) {
       print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="string">
  The passphrase-encrypted JSON data containing recovery key shares, created by the [Export recovery key shares](https://www.cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/export-recovery-key-shares) or [Export Secrets](https://www.cobo.com/developers/v2/developer-tools/ucw-sdk/ucw-class/export-secrets) operations.
</ParamField>

<ParamField type="string">
  The passphrase used to decrypt the JSON data of recovery key shares.
</ParamField>


# Recover private keys
Source: https://cobo.com/developers/v2/developer-tools/ucw-sdk/ucwrecoverkey-class/recover-private-keys

This operation recovers the full private keys for the specified addresses using recovery key shares imported via the [Import recovery key share](https://www.cobo.com/developers/v2/developer-tools/ucw-sdk/ucwrecoverkey-class/import-recovery-key-share) operation.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

<CodeGroup>
  ```Swift iOS theme={null}
  public func recoverPrivateKeys(addressInfos: [AddressInfo]) throws -> [PrivateKeyInfo]
  ```

  ```Dart Flutter theme={null}
  Future<List<PrivateKeyInfo>> recoverPrivateKeys(List<AddressInfo> addressInfos) async
  ```
</CodeGroup>

<RequestExample>
  ```Swift iOS theme={null}
  let addressInfos: [AddressInfo] = [
      AddressInfo(bip32Path: "m/44/1/1/0/0", pubKey: "xpub6FRrW2AzsDQcVQPNCCQgiB7xSQ9UseQfrRCJdD9qjWswrNBmY1MysLdMYxpWbB1mnGJTwLCZWCfA4ko2kQNN37CPSzidD1c9aZCBXjTzfQn")
      AddressInfo(bip32Path: "m/44/1/1/0/1", pubKey: "xpub6FRrW2AzsDQcZahYm2GgsDz7VtqgkvNwR58boDejvwSuCYZ2ZRVvqP6Gaqef6hMGxKtkvj3PfcRxagKSycuh6XX7kJ3Bzc2vUrEAA4at5Jc")
  ]

  do {
      let privateKeyInfos = try recoverKey?.recoverPrivateKeys(addressInfos: addressInfos)
      if let privateKeyInfos = privateKeyInfos {
          for privateKeyInfo in privateKeyInfos {
              print("Private Key Info: \(privateKeyInfo)")
          }
      } else {
          print("Failed to recover private keys.")
      }
  } catch {
      print("Error: \(error)")
  }
  ```

  ```Dart Flutter theme={null}
  final List<AddressInfo> addressInfos = [
      AddressInfo(
          bip32Path: "m/44/1/1/0/0",
          pubKey: "xpub6FRrW2AzsDQcVQPNCCQgiB7xSQ9UseQfrRCJdD9qjWswrNBmY1MysLdMYxpWbB1mnGJTwLCZWCfA4ko2kQNN37CPSzidD1c9aZCBXjTzfQn"
      ),
      AddressInfo(
          bip32Path: "m/44/1/1/0/1",
          pubKey: "xpub6FRrW2AzsDQcZahYm2GgsDz7VtqgkvNwR58boDejvwSuCYZ2ZRVvqP6Gaqef6hMGxKtkvj3PfcRxagKSycuh6XX7kJ3Bzc2vUrEAA4at5Jc"
      ),
  ];

  try {
      final privateKeyInfos = await recoverKey?.recoverPrivateKeys(addressInfos: addressInfos);
      for (final privateKeyInfo in privateKeyInfos) {
          print("Private Key Info: $privateKeyInfo");
      }
  } catch (error) {
      print("Error: $error");
  }
  ```
</RequestExample>

## Parameters

<ParamField type="object[]">
  A list of address information objects, each containing the BIP32 path and the optional root extended public key, required to recover the corresponding private keys.

  <Expandable title="child attributes">
    <ParamField type="string">
      The BIP32 path of the address.
      For example: `m/44/1/1/0/0`.
    </ParamField>

    <ParamField type="string">
      The extended public key of the address. This parameter is optional and can be left empty. If provided, the derived public key will be compared against this value during the key derivation process. A mismatch will result in an error.
    </ParamField>
  </Expandable>
</ParamField>

## Response

<ResponseField name="privateKeyInfos" type="object[]">
  The list of objects containing the recovered private keys and their corresponding addresses.

  <Expandable title="child attributes">
    <ResponseField name="bip32Path" type="string">
      The BIP32 path for the address.
      For example: `m/44/1/1/0/0`.
    </ResponseField>

    <ResponseField name="publicKey" type="string">
      The extended public key for the address.
      For example: `xpub6FRrW2AzsDQcVQPNCCQgiB7xSQ9UseQfrRCJdD9qjWswrNBmY1MysLdMYxpWbB1mnGJTwLCZWCfA4ko2kQNN37CPSzidD1c9aZCBXjTzfQn`.
    </ResponseField>

    <ResponseField name="privateKey" type="object">
      Different formats of private keys corresponding to the address.

      <Expandable title="child attributes">
        <ResponseField name="extPrivateKey" type="string">
          The root extended private key.
        </ResponseField>

        <ResponseField name="hexPrivateKey" type="string">
          The private key in hexadecimal format.
        </ResponseField>
      </Expandable>
    </ResponseField>
  </Expandable>
</ResponseField>


# UI Toolkit API reference
Source: https://cobo.com/developers/v2/developer-tools/uitoolkit-api

Explore the Cobo UI Toolkit API for efficient app development. Access hooks, functions, and types for seamless integration.

## Types

### AuthInfo

The authentication information of a user.

#### Properties

| Name              | Type   | Description                                                |
| ----------------- | ------ | ---------------------------------------------------------- |
| token             | string | The [User Info Token](/developers/v2/apps/verify-users).              |
| orgID             | string | The user's organization ID.                                |
| userID            | string | The user ID.                                               |
| (Optional) action | string | The current operation type. You can ignore this parameter. |

### MfaListItem

The information about a multi-factor authentication (MFA) method that will be displayed in the UI.

#### Properties

| Name      | Type   | Description                                                                                                                                                                                                                                                                                                             |
| --------- | ------ | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| mfaMethod | string | The MFA method type. The possible values are as follows:<ul><li>`google_auth`: Google Authenticator.</li><li>`cobo_guard`: Cobo Guard.</li><li>`security_key`: Security keys.</li></ul> For more details, refer to [Set up multi-factor authentication (MFA) methods](https://manuals.cobo.com/en/accounts/set-up-mfa). |
| mfaStatus | string | The active status of the MFA method. The possible values are as follows:<ul><li>`Active`: The MFA method will be displayed as enabled in the UI.</li><li>`Inactive`(default): The MFA method will be displayed as disabled in the UI.</li></ul>Any other values will be treated as `Inactive`.                          |

## Enums

### locale

The language setting.

* `en-US`: English.
* `zh-CN`: Chinese.

## Hooks

### useMFA

```typescript theme={null}
const useMFA: () => (mfaMethods: MfaListItem[]) => Promise<string>;
```

This hook manages multi-factor authentication (MFA) methods within your application. It provides a function to send MFA method data to Cobo for processing.

#### Returns

This hook returns a function `sendMfaMethods` that sends an array of MFA methods to Cobo's backend.

The `sendMfaMethods`function has the following parameter:

| Name       | Type            | Description                                                                                                             |
| ---------- | --------------- | ----------------------------------------------------------------------------------------------------------------------- |
| mfaMethods | MfaListItem \[] | An array of [MfaListItem](#mfalistitem) objects. Each object represents an MFA method that will be displayed in the UI. |

The `sendMfaMethods` function returns a Promise that resolves to a request ID of string type, which should be sent to Cobo Portal for processing.

#### Sample code

The following example defines an array of MFA methods, sends them using `sendMfaMethods`, and handles the response or any errors.

```typescript theme={null}
import React, { useEffect } from 'react';
import { useMFA } from '@cobo/cobo-ui-toolkit';

const MyComponent = () => {
 const { sendMfaMethods } = useMFA();
 const testMFA = async () => {
  const mfaMethods = [
   { mfaMethod: "google_auth", mfaStatus: "Active" },
   { mfaMethod: "cobo_guard", mfaStatus: "Active" },
   { mfaMethod: "security_key", mfaStatus: "Active" },
  ];
  try {
   const requestId = await sendMfaMethods(mfaMethods);
   console.log('Request ID:', requestId);
  } catch (error) {
   console.error('Error sending MFA methods:', error);
  }
 };

 useEffect(() => {
  testMFA();
 }, []);
 return <div>Check console for request ID.</div>;
};

export default MyComponent;
```

### useTrackingScript

```typescript theme={null}
const useTrackingScript: (env: "production") => void;
```

This hook injects a tracking script into the DOM, which collects data for app analytics, and ensures proper cleanup when the component unmounts. This data will be accessible on Developer Console in the future.

#### Parameters

| Name | Type   | Description                                                                                                                                                                                                                                                                           |
| ---- | ------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| env  | string | The type of environment in which your app runs. For more details, refer to [environments](/developers/v2/guides/overview/environments).<br />Currently, this parameter value must be `production`, regardless of whether your app runs in the production environment or development environment. |

#### Sample code

The following example loads a tracking script in both the production and development environments.

```typescript theme={null}
import React from 'react';
import { useTrackingScript } from '@cobo/cobo-ui-toolkit';

const MyApp = () => {
  useTrackingScript('production');
  return <h1>Hello world</h1>;
};

export default MyApp;
```

#### Notes

To enable effective tracking, each clickable element in your app needs a unique tracking attribute named `data-track-id` or `dtid`. This attribute serves as the primary identifier for tracking interactions on specific buttons or elements, enabling consistent and accurate analytics collection.

Each `data-track-id` or `dtid` attribute value must be lowercase words separated by underscores in the format `{PAGE_IDENTIFIER}_{COMPONENT_IDENTIFIER}_{ELEMENT_IDENTIFIER}` that follow the following rules:

* Page identifier: Identifying the page or module's feature, including `home`, `login`, and `profile`.
* Component identifier: Identifies the specific UI component within the page, including `form`, `navbar`, `modal`, `search_bar`, `button`, `banner`, `icon_button`, `tab`, `switch_button`, `checkbox`, `radio`, `sidebar`, `footer`, `header`, and `link`.
* Element identifier: Identifies the button or interactive element, including `submit`, `register`, and `next_step`.

For example, the attribute value for a submit button on the home page can be `home_form_submit`.

When an element contains child elements, avoid using event-blocking methods such as `stopPropagation()` and `preventDefault()` because they can interfere with effective click tracking. In typical cases, you only need to apply the `data-track-id` or `dtid` attribute to the parent element, as child elements will automatically inherit it for tracking purposes.

The following example shows how to implement this:

```html theme={null}
<button data-track-id="home_form_submit">
  <span>Child Element 1</span>
</button>
```

However, if using the event-blocking methods is necessary, ensure that each child element within the parent has the same tracking attribute to maintain accurate tracking.

**Input field collection rules**

For input fields with a `data-track-id`, the user input and the value of `data-track-id` will be collected for analyzing user behavior.

In the following example, the keywords entered by the user and the value of `home_search_bar_wallet` will be collected.

```html theme={null}
<input type="text" data-track-id="home_search_bar_wallet" placeholder="Enter keywords" />
```

For sensitive information such as passwords and personal identification information, you can mark an input field as containing sensitive information by using `data-track-sensitive="true"`, which will tell the tracking script to automatically ignore the data and not collect it.

In the following example, the password entered by the user will not be collected by the tracking script.

```html theme={null}
<input type="password" data-track-id="login_form_password" data-track-sensitive="true" placeholder="Enter your password" />
```

If an input field is nested within other components (such as a form), the parent `data-track-id` will not override or replace the input field's own `data-track-id`.

In the following example, the `data-track-id` of the input field is `login_form_email`, not `login_form`.

```html theme={null}
<form data-track-id="login_form">
   <input type="text" data-track-id="login_form_email" placeholder="Email" />
</form>
```

### useAddUidToBody

```typescript theme={null}
const useAddUidToBody: (userId: string) => void;
```

This hook converts a specified user ID from string to Base64 format and adds it as a `uid` attribute to the `<body>` tag of the HTML document. It is useful in scenarios where a user ID needs to be incorporated into the document structure for global tracking or analytics.

#### Parameters

| Name   | Type   | Description                                  |
| ------ | ------ | -------------------------------------------- |
| userId | string | The user ID to be added to the `<body>` tag. |

#### Sample code

The following example uses the `useAddUidToBody` function to add a `uid` attribute to the `<body>` tag with the user ID. When the user ID changes, the value of the `uid` attribute is updated accordingly.

```typescript theme={null}
import React from 'react';
import { useAddUidToBody } from '@cobo/cobo-ui-toolkit';

const UserProfile = () => {
  const userId = 'user123';

  useAddUidToBody(userId);

  return (
    <div>
      <h1>Hello,user {userId}</h1>
    </div>
  );
};

export default UserProfile;
```

## Functions

### getAuthInfo

```typescript theme={null}
type AuthInfo = {
    token: string;
    orgID: string;
    userID?: string;
};
const getAuthInfo: () => Promise<AuthInfo | undefined>;
```

This asynchronous function retrieves user authentication information from [Cobo Portal](https://manuals.cobo.com/en/portal/introduction).

#### Returns

* `Promise<[AuthInfo]>`: For more details, refer to [AuthInfo](#authinfo).
* `undefined`: The authentication information is unavailable or the request fails.

#### Sample code

The following example retrieves user authentication information using the `getAuthInfo` function when the component mounts and displays that information.

```typescript theme={null}
import React, { useEffect, useState } from 'react';
import { getAuthInfo } from '@cobo/cobo-ui-toolkit';

const UserProfile = () => {
  const [authInfo, setAuthInfo] = useState<AuthInfo | undefined>(undefined);

  useEffect(() => {
    const fetchAuthInfo = async () => {
      const info = await getAuthInfo();
      setAuthInfo(info);
    };

    fetchAuthInfo();
  }, []);

  if (!authInfo) {
    return <div>Loading...</div>;
  }

  return (
    <div>
      <h1>User Information</h1>
      <p>Token: {authInfo.token}</p>
      <p>Organization ID: {authInfo.orgID}</p>
      {authInfo.userID && <p>User ID: {authInfo.userID}</p>}
    </div>
  );
};

export default UserProfile;
```

### parseJwtToken

```typescript theme={null}
const parseJwtToken: (token: string) => any;
```

This function parses a JSON Web Token (JWT) and returns the payload as a JSON object. Use this function to extract user information, permissions, and other related information in a JWT.

You can use this function to parse the [User Info Token](/developers/v2/apps/verify-users), which contains the information of a Cobo Portal App user.

#### Parameters

| Name  | Type   | Description                                                                       |
| ----- | ------ | --------------------------------------------------------------------------------- |
| token | string | The JWT string to be parsed. It must be in the `header.payload.signature` format. |

#### Returns

If the token is a valid JWT, the function returns the payload as a JSON object.

#### Errors

If the token format is incorrect or cannot be parsed, the function throws an error with messages such as:

* `Invalid Base64 encoding`: The payload part of the token is not properly Base64 encoded.
* `Invalid token format`: There is an issue parsing the token, for example, incorrect structure or failure to decode.

#### Sample code

The following example uses the `parseJwtToken` function to parse a User Info Token and logs the decoded payload to the console.

```typescript theme={null}
import { parseJwtToken } from '@cobo/cobo-ui-toolkit';

const token =
  'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c';

try {
  const payload = parseJwtToken(token);
  console.log(payload);
} catch (error) {
  console.error(error.message);
}
```

### verifyJwtToken

```typescript theme={null}
const verifyJwtToken: (token: string, publicKeySet: any) => Promise<boolean>;
```

This function verifies a JSON Web Token (JWT) using the specified public keys, ensuring that the token has not been tampered with and is valid.

You can use this function to verify a Cobo Portal App user's identity. Refer to [User Info Tokens](/developers/v2/apps/verify-users) for more information.

#### Parameters

| Name         | Type   | Description                                                                                                                                                |
| ------------ | ------ | ---------------------------------------------------------------------------------------------------------------------------------------------------------- |
| token        | string | The JWT to be verified. It must be in the `header.payload.signature format`.                                                                               |
| publicKeySet | any    | A set of public keys used to verify the JWT signature. Each public key should have a `kid` attribute, which matches the `kid` attribute in the JWT header. |

#### Returns

* `true`: The JWT is valid.
* `false`: The JWT is invalid.

#### Sample code

The following example verifies a User Info Token with the public key set retrieved from the specified URL. If the verification is successful, it extracts the information from the User Info Token and sets the information as the user's information.

```typescript theme={null}
import { parseJwtToken, verifyJwtToken } from '@cobo/cobo-ui-toolkit';

get('https://api.dev.cobo.com/v2/oauth/authorize/jwks.json').then(async (res) => {
  const verified = await verifyJwtToken(token, res);
  if (!verified) return;
  const jwtInfo = parseJwtToken(token);
  setUserInfo({
    email: jwtInfo.email,
    roleNames: jwtInfo.role_names,
    roles: jwtInfo.roles,
    sub: jwtInfo.sub,
  });
});
```

### getPortalLocale

```typescript theme={null}
type Locale = {

  locale: 'en-US' | 'zh-CN';

};
const getPortalLocale: (callback: (data: Locale) => void) => void;
```

This function listens for the current locale data of [Cobo Portal](https://manuals.cobo.com/en/portal/introduction) and executes a callback when the locale data updates.

<Note>Call [removeGetLocaleListener](#removegetlocalelistener) to clean up the listener when it is no longer needed, especially in components that may unmount.</Note>

#### Parameters

| Name     | Type     | Description                                                      |
| -------- | -------- | ---------------------------------------------------------------- |
| callback | function | A function that takes a [locale](#locale) object as an argument. |

#### Returns

`void`

#### Errors

`Failed to get locale`: The locale data is undefined.

#### Sample code

The following example listens for the locale data of Cobo Portal and logs it to the console when the data updates.

```typescript theme={null}
import { getPortalLocale } from '@cobo/cobo-ui-toolkit';

import WaasSkillReminder from '/snippets/waas_skill_reminder.mdx';

<WaasSkillReminder />

useEffect(() => {
  getPortalLocale((locale) => {
    console.log("locale", locale);
  });
}, []);
```

### removeGetLocaleListener

```typescript theme={null}
const removeGetLocaleListener: () => void;
```

This function removes the listener for the current locale data of [Cobo Portal](https://manuals.cobo.com/en/portal/introduction).

After you call [getPortalLocale](#getportallocale) to listen to the locale data, use this function to clean up the listener when it is no longer needed, especially in components that may unmount.


# Introduction to Cobo UI Toolkit
Source: https://cobo.com/developers/v2/developer-tools/uitoolkit-intro

Discover Cobo UI Toolkit for seamless Cobo Portal App development. Simplify tasks with utility functions and React integration.

<Tip>
  Try [Cobo WaaS Skill](/developers/v2/guides/overview/cobo-waas-skill) in your AI coding assistant (Claude Code, Cursor, etc.). Describe your needs in natural language to auto-generate production-ready SDK code and debug faster 🚀
</Tip>

Cobo UI Toolkit is a library designed primarily to facilitate communication between the front end of [Cobo Portal Apps](/developers/v2/apps/introduction) and [Cobo Portal](https://manuals.cobo.com/en/portal/introduction). This toolkit offers a collection of utilities that help you reduce coding effort, streamline development, and maintain consistency in user experience across applications.

## Key Features

* **Utility functions**: Provides a set of utility functions that simplify common tasks, such as multi-factor authentication (MFA) handling and app user verification, enhancing development efficiency and reducing boilerplate code.
* **Framework integration**: Designed for seamless integration with React, making it easy to incorporate into existing projects.

## Installation

To use Cobo UI Toolkit in your project, you first need to install it via npm. You can do this by running the following command in a terminal window:

```
npm install @cobo/cobo-ui-toolkit
```