# Manage endpoints

Use this page to manage endpoint address book entries. For the concept, see [Endpoints](/products/custody/accounts-and-assets/endpoints).

## Endpoint actions

| Action | UI procedure | API procedure | API reference |
|  --- | --- | --- | --- |
| Register an endpoint | [Register an endpoint in the UI](#register-an-endpoint-in-the-ui) | [Register an endpoint with the API](#register-an-endpoint-with-the-api) | [Propose an intent](/products/custody/reference/api/openapi/intents/createintent), [Perform a dry run](/products/custody/reference/api/openapi/intents/intentdryrun) |
| Register a smart contract endpoint | [Register an endpoint in the UI](#register-an-endpoint-in-the-ui) | [Register an endpoint with the API](#register-an-endpoint-with-the-api) | [Propose an intent](/products/custody/reference/api/openapi/intents/createintent), [Perform a dry run](/products/custody/reference/api/openapi/intents/intentdryrun) |
| View endpoint details | [View endpoints in the UI](#view-endpoints-in-the-ui) | [View endpoint details with the API](#view-endpoint-details-with-the-api) | [List endpoints](/products/custody/reference/api/openapi/endpoints/getendpoints), [Get endpoint details](/products/custody/reference/api/openapi/endpoints/getendpoint) |
| Update an endpoint | [Update an endpoint in the UI](#update-an-endpoint-in-the-ui) | [Update an endpoint with the API](#update-an-endpoint-with-the-api) | [Propose an intent](/products/custody/reference/api/openapi/intents/createintent), [Perform a dry run](/products/custody/reference/api/openapi/intents/intentdryrun) |
| Lock and unlock an endpoint | Use the API procedure. | [Lock or unlock an endpoint with the API](#lock-or-unlock-an-endpoint-with-the-api) | [Propose an intent](/products/custody/reference/api/openapi/intents/createintent), [Perform a dry run](/products/custody/reference/api/openapi/intents/intentdryrun) |


Endpoint changes use the standard intent flow. For signing, approval, and status checks, see [Manage intents and approvals](/products/custody/governance/intents/manage-intents-and-approvals), [Sign intents](/products/custody/identity-and-access/authentication/authenticate-api-requests#signing-intents-state-mutation-operations), and [Check updates](/products/custody/governance/intents/manage-intents-and-approvals#check-state).

Use endpoint API read operations to list and get endpoint records. Use endpoint intent payloads to create, update, lock, and unlock endpoint records. Submit endpoint intents to [Propose an intent](/products/custody/reference/api/openapi/intents/createintent). Use [Perform a dry run](/products/custody/reference/api/openapi/intents/intentdryrun) before you sign high-risk or unfamiliar payloads.

## Common operations

| Operation | Intent type | Use when |
|  --- | --- | --- |
| Register endpoint | `v0_CreateEndpoint` | Add a ledger address or smart contract address as a known destination. |
| Update endpoint | `v0_UpdateEndpoint` | Change endpoint details such as address, trust score, ABI data, or custom properties. |
| Lock endpoint | `v0_LockEndpoint` | Disable an endpoint without deleting it. |
| Unlock endpoint | `v0_UnlockEndpoint` | Re-enable a locked endpoint. |


## Register an endpoint in the UI

You can register a ledger address or, if the ledger supports smart contracts, a smart contract address as an endpoint.

If this is a smart contract endpoint, you can provide the contract application binary interface (ABI) data when you register the endpoint.

To register an endpoint:

1. Navigate to **Endpoints**.
2. Select **Create an endpoint**.
3. Enter the details of the endpoint, such as the name and description.
4. Select the ledger.
5. Enter the endpoint address.
6. If the endpoint address is a smart contract address, enter smart contract ABI details in one of the following ways:
  - Enter the ABI in JSON format.
  - Upload the ABI in a file.
7. Enter the trust score as a number from `0` to `100`.
8. Select **Submit for Approval** and [sign the operation with the app](/products/custody/identity-and-access/authentication/ui-authentication#sign-ui-operations).


The new endpoint is registered when the intent is successfully executed.

## Register an endpoint with the API

You can register a ledger address or, if the ledger supports smart contracts, a smart contract address as an endpoint.

If this is a smart contract endpoint, you can provide the contract application binary interface (ABI) data when you create the endpoint.

Before you register an endpoint, prepare:

| Prerequisite | Additional information |
|  --- | --- |
| Ledger ID | [List ledgers](/products/custody/reference/api/openapi/ledgers/getledgers) |
| Endpoint address | For a custody account address, [retrieve the account address](/products/custody/reference/api/openapi/accounts/getaccountaddress). For an external address or smart contract address, collect and validate the address before submission. |
| New IDs | Prepare an endpoint ID and an intent ID in standard UUID format. |


Create an endpoint by submitting a `v0_CreateEndpoint` intent.

Duplicate endpoint rejection
Endpoints are unique per domain, address, ledger, and destination tag or memo. If you create or update an endpoint that matches an existing endpoint on all four values, Ripple Custody rejects the intent, and a dry run reports the conflict. An empty destination tag counts as a value: only one endpoint without a tag can exist for a given domain, address, and ledger. To reuse an address, register each endpoint with a distinct destination tag or memo, or use the existing endpoint.

### Ledger address endpoint payload

```json
{
  "payload": {
    "id": "c3ddaca1-07d8-437d-803b-bfdef7833aa4",
    "address": "0x258aE861829FB6B33e7528308cA2938638590F34",
    "trustScore": 50,
    "ledgerId": "ethereum-testnet",
    "alias": "Ethereum Testnet",
    "lock": "Unlocked",
    "description": "Ethereum testnet wallet",
    "customProperties": {},
    "type": "v0_CreateEndpoint"
  }
}
```

### Smart contract endpoint payload

```json
{
  "payload": {
    "id": "b445e1d1-41fe-468a-a600-1b9ad7b057e1",
    "address": "0xb2f701a94d864b131fd47c9cf4563e6298afdbfc",
    "trustScore": 50,
    "ledgerId": "ethereum-testnet",
    "parameters": {
      "ABI": "<ABI_JSON_STRING>",
      "type": "Ethereum"
    },
    "alias": "MTT Smart Contract",
    "lock": "Unlocked",
    "description": "MTT token contract",
    "customProperties": {},
    "type": "v0_CreateEndpoint"
  }
}
```

Fields of the `payload` block to note are:

| Field | Description |
|  --- | --- |
| `type` | `v0_CreateEndpoint` |
| `id` | New endpoint ID in UUID format. |
| `address` | Ledger address or smart contract address. |
| `trustScore` | Score from `0` to `100` that policies can use to define destination-specific workflows. |
| `ledgerId` | Ledger that scopes the address. |
| `parameters` | Ledger-specific parameters. The `type` field selects the format. For smart contract endpoints, set `type` to `Ethereum` and `ABI` to the ABI string in JSON format. For destination tags and memos on XRPL, Stellar, and Hedera, see [Destination tag and memo payloads](#destination-tag-and-memo-payloads). |
| `alias` | Human-readable endpoint name. |
| `lock` | Initial lock state. Use `Unlocked` to make the endpoint available after approval. |
| `description` | Optional endpoint description. |
| `customProperties` | Required key-value metadata object with string values. Use `{}` when empty. |


Dry run before submitting:

```sh
curl -X POST "${CUSTODY_API_URL}/v1/intents/dry-run" \
  -H "Authorization: Bearer ${JWT_TOKEN}" \
  -H "Content-Type: application/json" \
  -d @create-endpoint-intent.json
```

Submit the signed intent:

```sh
curl -X POST "${CUSTODY_API_URL}/v1/intents" \
  -H "Authorization: Bearer ${JWT_TOKEN}" \
  -H "Content-Type: application/json" \
  -d @signed-create-endpoint-intent.json
```

The endpoint is registered when the endpoint creation intent is successfully approved and executed.

### Destination tag and memo payloads

On ledgers that route funds at a shared address by tag, store the tag on the endpoint in the `parameters` field. The endpoint is then the source of truth: transfers that use the endpoint as their destination carry its tag automatically.

| Ledger | `parameters` field | Format |
|  --- | --- | --- |
| XRPL | `destinationTag` | Integer, 0 to 4294967295 (32-bit unsigned). |
| Stellar | `memo` | One typed object: `Text` (1-28 bytes), `Id` (unsigned 64-bit integer as a string), `Hash` or `Return` (64-character hex). |
| Hedera | `memo` | UTF-8 string, 1 to 100 bytes. |


Ripple Custody validates the value against the target ledger's format when you create or update the endpoint and rejects invalid values.

An XRPL endpoint with a destination tag:

```json
{
  "payload": {
    "id": "8f4f4be6-1f4e-4a2b-9b6d-1d1b6f0f2a10",
    "address": "rEXAMPLEaBcDeFgHiJkLmNoPqRsTuVwXyZ",
    "trustScore": 50,
    "ledgerId": "xrpl-testnet",
    "parameters": {
      "destinationTag": 745692,
      "type": "XRPL"
    },
    "alias": "Exchange deposit account",
    "lock": "Unlocked",
    "description": "Exchange omnibus address, customer tag 745692",
    "customProperties": {},
    "type": "v0_CreateEndpoint"
  }
}
```

A Stellar endpoint uses a typed memo object instead, for example `"memo": { "value": "745692", "type": "Id" }`; a Hedera endpoint uses a plain string, `"memo": "customer-745692"`.

## View endpoints in the UI

To view endpoints in the UI:

1. Navigate to **Endpoints**.
2. Review the endpoint list.
3. Open an endpoint to review its details.


The endpoint list shows known destinations in the selected domain.

## View endpoint details with the API

To view endpoint details:

1. If you do not know the endpoint ID, retrieve a list of endpoints in the domain with [List endpoints](/products/custody/reference/api/openapi/endpoints/getendpoints). You can filter the list by ledger with the `ledgerId` query parameter.
2. Retrieve endpoint details with [Get endpoint details](/products/custody/reference/api/openapi/endpoints/getendpoint), using the endpoint ID from step 1.


Use `List endpoints` query parameters to narrow or sort endpoint lists:

| Task | Query parameter |
|  --- | --- |
| Filter by ledger | `ledgerId` |
| Filter by alias | `alias` |
| Filter by address | `address` |
| Filter by description | `metadata.description` |
| Filter by creator | `metadata.createdBy` |
| Filter by last modifier | `metadata.lastModifiedBy` |
| Filter by lock state | `lock` |
| Filter by custom properties | `metadata.customProperties` |
| Paginate results | `limit`, `startingAfter` |
| Sort results | `sortBy`, `sortOrder` |


The API returns trusted endpoint objects. Inspect the `data` object for endpoint details.

Depending on the endpoint type, `data` includes:

- Endpoints that are ledger addresses do not include ABI data in the `parameters` field.
- Endpoints that are associated with a smart contract address have ABI data in the `parameters` field in JSON format.


The `data` object also includes `domainId`, `metadata`, `lock`, and `trustScore` so you can confirm ownership, revision, availability, and policy inputs before you use the endpoint in a transaction order. The trusted endpoint envelope also includes `signature` and `signingKey`.

## Update an endpoint in the UI

You can update the following details of an endpoint:

- Name and description.
- Address.
- Trust score.
- Custom properties.


You cannot update the ledger.

To update an endpoint:

1. Navigate to **Endpoints**.
2. At the end of the endpoint row, open the contextual menu and select **Edit**.
3. Update the details of the endpoint.
4. Select **Submit for Approval** and [sign the operation with the app](/products/custody/identity-and-access/authentication/ui-authentication#sign-ui-operations).


The endpoint details are updated when the intent is successfully executed.
Ripple Custody increases the endpoint revision.

## Update an endpoint with the API

You can update general details of an endpoint such as the address and the trust score. For a smart contract endpoint, you can also update the application binary interface (ABI) data.

Endpoint updates use a `v0_UpdateEndpoint` intent. Submit the update through the standard intent flow, then check the endpoint after execution.

Do not include `ledgerId` in endpoint update payloads. The API specification marks `ledgerId` as deprecated for `v0_UpdateEndpoint`, and you cannot update the ledger in the UI.

Omit `parameters` unless you update ABI data for a smart contract endpoint or a destination tag/memo (see [Update a destination tag or memo](#update-a-destination-tag-or-memo)).

```json
{
  "payload": {
    "reference": {
      "id": "c3ddaca1-07d8-437d-803b-bfdef7833aa4",
      "revision": 2
    },
    "address": "0x258aE861829FB6B33e7528308cA2938638590F34",
    "trustScore": 75,
    "alias": "Ethereum treasury endpoint",
    "description": "Updated Ethereum treasury destination",
    "customProperties": {},
    "type": "v0_UpdateEndpoint"
  }
}
```

For a smart contract endpoint, include the `parameters` object with the updated ABI data:

```json
{
  "parameters": {
    "ABI": "<ABI_JSON_STRING>",
    "type": "Ethereum"
  }
}
```

### Update a destination tag or memo

The `v0_UpdateEndpoint` payload accepts the same `parameters` field as creation, so you can add, change, or clear an endpoint's destination tag or memo. Ripple Custody validates the update against the same per-ledger format rules and the same uniqueness rule: it rejects an update that would collide with an existing endpoint on domain, address, ledger, and destination tag, and a dry run reports the conflict before you submit.

## Lock or unlock an endpoint with the API

Endpoint lock-state changes use the standard intent flow.

| Update | Intent type | Additional information |
|  --- | --- | --- |
| Lock an endpoint | `v0_LockEndpoint` | [Submit an intent](/products/custody/governance/intents/manage-intents-and-approvals#submit-an-intent-with-the-api) |
| Unlock an endpoint | `v0_UnlockEndpoint` | [Submit an intent](/products/custody/governance/intents/manage-intents-and-approvals#submit-an-intent-with-the-api) |


Submit a lock intent with the current endpoint reference:

```json
{
  "payload": {
    "reference": {
      "id": "c3ddaca1-07d8-437d-803b-bfdef7833aa4",
      "revision": 2
    },
    "type": "v0_LockEndpoint"
  }
}
```

Use `v0_UnlockEndpoint` with the same reference shape to re-enable the endpoint.

## Operational checklist

Before submitting an endpoint intent:

- Confirm the endpoint is in the correct domain.
- Confirm the ledger and address are correct.
- Confirm the trust score matches your policy model.
- Confirm whether the endpoint represents a smart contract and needs ABI data.
- Dry run the payload when using the API.
- Verify the executed change by viewing the endpoint.