> This page is for Taurus PROTECT, version v3.54.
> For other versions, use one of these documentation indexes:
> - v3.58 (default): https://taurushq.ferndocs.com/protect-capital/v3.58/llms.txt
> - v3.56: https://taurushq.ferndocs.com/protect-capital/v3.56/llms.txt
> - v3.54: https://taurushq.ferndocs.com/protect-capital/v3.54/llms.txt
> - v3.52: https://taurushq.ferndocs.com/protect-capital/v3.52/llms.txt
> - v3.50: https://taurushq.ferndocs.com/protect-capital/v3.50/llms.txt
> - v3.48: https://taurushq.ferndocs.com/protect-capital/v3.48/llms.txt
> - v3.46: https://taurushq.ferndocs.com/protect-capital/v3.46/llms.txt
> - v3.44: https://taurushq.ferndocs.com/protect-capital/v3.44/llms.txt
> - v3.42: https://taurushq.ferndocs.com/protect-capital/v3.42/llms.txt
> - v3.40: https://taurushq.ferndocs.com/protect-capital/v3.40/llms.txt
> - v3.38: https://taurushq.ferndocs.com/protect-capital/v3.38/llms.txt

> For clean Markdown of any page, append .md to the page URL.
> For a complete documentation index, see https://taurushq.ferndocs.com/llms.txt.
> For AI client integration (Claude Code, Cursor, etc.), connect to the MCP server at https://taurushq.ferndocs.com/_mcp/server.

# Burn tokens

POST https://your-protect-instance.example.com/api/rest/v2/assets/{assetID}/burn
Content-Type: application/json

Starts a burn operation for the given asset.

Reference: https://taurushq.ferndocs.com/protect-capital/reference/assets-v2/burn-asset-v-2

## Authentication

- `Authorization` header (bearer token, required) — Bearer authentication of the form `Bearer <token>`, where token is your auth token.

## Request

### Path parameters

- `assetID` (string, required)

### Body (application/json)

This endpoint expects an AssetServiceV2BurnAssetV2Body.

- `fromAddressID` (string, optional)
- `destination` (tgvalidatordAddressTargetV2, optional) — AddressTargetV2 names an address as either an internal address (managed by the platform) or a whitelisted external address. Exactly one variant must be set. Replaces v1's paired uint64 fields where mutual exclusion was a runtime invariant.
- `amount` (string, optional)
- `nftTokenIDs` (list of string, optional)

## Response

### 200

A successful response.

- `id` (string, optional)
- `assetID` (string, optional)
- `type` (enum, optional)
  - Allowed values: `ASSET_OPERATION_TYPE_V2_CREATE`, `ASSET_OPERATION_TYPE_V2_UPDATE`, `ASSET_OPERATION_TYPE_V2_IMPORT`, `ASSET_OPERATION_TYPE_V2_MINT`, `ASSET_OPERATION_TYPE_V2_BURN`, `ASSET_OPERATION_TYPE_V2_PAUSE`, `ASSET_OPERATION_TYPE_V2_UNPAUSE`, `ASSET_OPERATION_TYPE_V2_PAUSE_ACCOUNT`, `ASSET_OPERATION_TYPE_V2_UNPAUSE_ACCOUNT`, `ASSET_OPERATION_TYPE_V2_SET_KYC`
- `status` (enum, optional) — AssetOperationStatusV2 is the consumer-facing lifecycle status of an operation. Two non-terminal values: - PENDING: system is making progress automatically; consumer should wait. - PAUSED: action required from the operation initiator (or an operator) before progress can resume — see AssetOperationV2.blockingReason for the machine-readable cause. Three terminal values: COMPLETED, FAILED, CANCELED.
  - Allowed values: `ASSET_OPERATION_STATUS_V2_PENDING`, `ASSET_OPERATION_STATUS_V2_PAUSED`, `ASSET_OPERATION_STATUS_V2_COMPLETED`, `ASSET_OPERATION_STATUS_V2_FAILED`, `ASSET_OPERATION_STATUS_V2_CANCELED`
- `createdAt` (datetime, optional)
- `updatedAt` (datetime, optional)
- `initiatedByAddressID` (string, optional) — Internal address that initiated this operation.
- `failureReason` (enum, optional) — AssetOperationFailureReasonV2 is the machine-readable cause when an operation reaches the FAILED terminal status. Free-form failure messages are not surfaced on the wire; consumers should switch on this enum. Two-tier: UNSPECIFIED means not failed; UNKNOWN is the catch-all for failed-with-no-typed-code; specific reasons grow as concrete cases are wired through from the underlying workflows. - ASSET_OPERATION_FAILURE_REASON_V2_UNKNOWN: Failed, but no typed code is available - ASSET_OPERATION_FAILURE_REASON_V2_INTERNAL_ERROR: Specific: a system/internal error occurred. - ASSET_OPERATION_FAILURE_REASON_V2_REQUEST_REJECTED: The underlying approval request was rejected by an approver. - ASSET_OPERATION_FAILURE_REASON_V2_REQUEST_FAILED: The underlying request terminated in failure for some non-rejection reason (expired, timed out, on-chain failure, ...). - ASSET_OPERATION_FAILURE_REASON_V2_SOURCE_ADDRESS_ON_INVALID_CURRENCY: The source address passed to the operation is registered for a different currency than the asset. One must retry with the address tied to the asset's currency. - ASSET_OPERATION_FAILURE_REASON_V2_SOURCE_ADDRESS_NOT_ASSET_ISSUER: The source address isn't the asset's on-chain issuer (the per-chain name varies. Only the issuer can mint or burn the asset.
  - Allowed values: `ASSET_OPERATION_FAILURE_REASON_V2_UNKNOWN`, `ASSET_OPERATION_FAILURE_REASON_V2_INTERNAL_ERROR`, `ASSET_OPERATION_FAILURE_REASON_V2_REQUEST_REJECTED`, `ASSET_OPERATION_FAILURE_REASON_V2_REQUEST_FAILED`, `ASSET_OPERATION_FAILURE_REASON_V2_SOURCE_ADDRESS_ON_INVALID_CURRENCY`, `ASSET_OPERATION_FAILURE_REASON_V2_SOURCE_ADDRESS_NOT_ASSET_ISSUER`
- `blockingReason` (enum, optional) — AssetOperationBlockingReasonV2 is the machine-readable cause when an operation is in the PAUSED non-terminal status. Distinct from FailureReason: a paused operation is alive and resumable once the blocker is cleared. Two-tier same as FailureReason: UNSPECIFIED means not paused; UNKNOWN is the catch-all for paused-with-no-typed-code; specific reasons grow as concrete cases land. - ASSET_OPERATION_BLOCKING_REASON_V2_UNKNOWN: Paused, but no typed code is available. - ASSET_OPERATION_BLOCKING_REASON_V2_MISSING_GOVERNANCE_RULE: Governance rule missing to complete the operations. - ASSET_OPERATION_BLOCKING_REASON_V2_MANUAL_PAUSE: Operation has been manually paused. - ASSET_OPERATION_BLOCKING_REASON_V2_AWAITING_REQUEST_APPROVAL: Awaiting human approval on a deployment / mint / burn / etc. request (the HandleRequestWorkflow's PENDING state). - ASSET_OPERATION_BLOCKING_REASON_V2_AWAITING_WHITELIST_APPROVAL: Awaiting approval of a whitelisted-address record for the asset. - ASSET_OPERATION_BLOCKING_REASON_V2_AWAITING_CURRENCY_PRICE: Operation blocked because no price is set for the asset's currency. - ASSET_OPERATION_BLOCKING_REASON_V2_AWAITING_MANUAL_WHITELIST: The auto-generated whitelist proposal was rejected by an approver; the asset is on-chain but the workflow waits for someone to manually create + approve a whitelist (which resumes the flow).
  - Allowed values: `ASSET_OPERATION_BLOCKING_REASON_V2_UNKNOWN`, `ASSET_OPERATION_BLOCKING_REASON_V2_MISSING_GOVERNANCE_RULE`, `ASSET_OPERATION_BLOCKING_REASON_V2_MANUAL_PAUSE`, `ASSET_OPERATION_BLOCKING_REASON_V2_AWAITING_REQUEST_APPROVAL`, `ASSET_OPERATION_BLOCKING_REASON_V2_AWAITING_WHITELIST_APPROVAL`, `ASSET_OPERATION_BLOCKING_REASON_V2_AWAITING_CURRENCY_PRICE`, `ASSET_OPERATION_BLOCKING_REASON_V2_AWAITING_MANUAL_WHITELIST`
- `create` (tgvalidatordCreateOperationDetailsV2, optional)
- `update` (tgvalidatordUpdateOperationDetailsV2, optional)
- `import` (tgvalidatordImportOperationDetailsV2, optional)
- `mint` (tgvalidatordMintOperationDetailsV2, optional)
- `burn` (tgvalidatordBurnOperationDetailsV2, optional)
- `pause` (tgvalidatordPauseOperationDetailsV2, optional)
- `unpause` (tgvalidatordUnpauseOperationDetailsV2, optional)
- `pauseAccount` (tgvalidatordPauseAccountOperationDetailsV2, optional)
- `unpauseAccount` (tgvalidatordUnpauseAccountOperationDetailsV2, optional)
- `setKyc` (tgvalidatordSetKYCOperationDetailsV2, optional)

## Errors

### 400 Bad Request Error

Bad Request: indicates that the server cannot or will not process the request due to something that is perceived to be a client error (for example, malformed request syntax, invalid request message framing, or deceptive request routing)

- `any`

### 401 Unauthorized Error

Unauthorized: indicates that the client request has not been completed because it lacks valid authentication credentials for the requested resource

- `any`

### 403 Forbidden Error

Forbidden: indicates that the server understands the request but refuses to authorize it

- `any`

### 404 Not Found Error

Not Found: indicates that the server cannot find the requested resource

- `any`

### 500 Internal Server Error

Internal Server Error: indicates that the server encountered an unexpected condition that prevented it from fulfilling the request

- `any`

### 503 Service Unavailable Error

Service Unavailable: indicates that the server is not ready to handle the request.

- `any`

## Types

### tgvalidatordAddressTargetV2

AddressTargetV2 names an address as either an internal address (managed by the platform) or a whitelisted external address. Exactly one variant must be set. Replaces v1's paired uint64 fields where mutual exclusion was a runtime invariant.

- `addressID` (string, optional) — Internal address identifier.
- `whitelistedAddressID` (string, optional) — Whitelisted address identifier.

### tgvalidatordCreateOperationDetailsV2

- `label` (string, optional)
- `price` (string, optional)
- `decimals` (string, optional)
- `params` (tgvalidatordAssetParamsV2, optional) — AssetParamsV2 carries blockchain-specific params for asset creation. Exactly one branch must be set. Non-Canton branches are INTERNAL at launch — drop the field_visibility marker to re-expose.
- `blockchain` (string, optional) — Blockchain/network/assetType the asset is being created on. Frozen at request time; carried on the op row so consumers can see the deployment target without joining AssetResourceV2.
- `network` (string, optional)
- `assetType` (string, optional)

### tgvalidatordUpdateOperationDetailsV2

- `label` (string, optional)
- `price` (string, optional)
- `params` (tgvalidatordUpdateAssetParamsV2, optional) — UpdateAssetParamsV2 mirrors AssetParamsV2's shape so callers learn one pattern. Branches for chains that don't support update today are empty messages; populating them later is non-breaking.

### tgvalidatordImportOperationDetailsV2

- `blockchain` (string, optional)
- `network` (string, optional)
- `label` (string, optional)
- `price` (string, optional)
- `decimals` (string, optional)
- `address` (string, optional)
- `params` (tgvalidatordImportAssetParamsV2, optional) — ImportAssetParamsV2 mirrors AssetParamsV2's shape for importing an existing on-chain asset.

### tgvalidatordMintOperationDetailsV2

- `destination` (tgvalidatordAddressTargetV2, optional) — AddressTargetV2 names an address as either an internal address (managed by the platform) or a whitelisted external address. Exactly one variant must be set. Replaces v1's paired uint64 fields where mutual exclusion was a runtime invariant.
- `amount` (string, optional)
- `nftMetadata` (list of string, optional)

### tgvalidatordBurnOperationDetailsV2

- `destination` (tgvalidatordAddressTargetV2, optional) — AddressTargetV2 names an address as either an internal address (managed by the platform) or a whitelisted external address. Exactly one variant must be set. Replaces v1's paired uint64 fields where mutual exclusion was a runtime invariant.
- `amount` (string, optional)
- `nftTokenIDs` (list of string, optional)

### tgvalidatordPauseOperationDetailsV2

### tgvalidatordUnpauseOperationDetailsV2

### tgvalidatordPauseAccountOperationDetailsV2

- `target` (tgvalidatordAddressTargetV2, optional) — AddressTargetV2 names an address as either an internal address (managed by the platform) or a whitelisted external address. Exactly one variant must be set. Replaces v1's paired uint64 fields where mutual exclusion was a runtime invariant.

### tgvalidatordUnpauseAccountOperationDetailsV2

- `target` (tgvalidatordAddressTargetV2, optional) — AddressTargetV2 names an address as either an internal address (managed by the platform) or a whitelisted external address. Exactly one variant must be set. Replaces v1's paired uint64 fields where mutual exclusion was a runtime invariant.

### tgvalidatordSetKYCOperationDetailsV2

- `target` (tgvalidatordAddressTargetV2, optional) — AddressTargetV2 names an address as either an internal address (managed by the platform) or a whitelisted external address. Exactly one variant must be set. Replaces v1's paired uint64 fields where mutual exclusion was a runtime invariant.
- `status` (enum, optional)
  - Allowed values: `KYC_STATUS_V2_APPROVED`, `KYC_STATUS_V2_REVOKED`

### tgvalidatordAssetParamsV2

AssetParamsV2 carries blockchain-specific params for asset creation. Exactly one branch must be set. Non-Canton branches are INTERNAL at launch — drop the field_visibility marker to re-expose.

- `cantonNativeTokenParams` (tgvalidatordCantonNativeTokenParamsV2, optional)

### tgvalidatordUpdateAssetParamsV2

UpdateAssetParamsV2 mirrors AssetParamsV2's shape so callers learn one pattern. Branches for chains that don't support update today are empty messages; populating them later is non-breaking.

- `hederaUpdateNativeTokenParams` (tgvalidatordHederaUpdateNativeTokenParamsV2, optional)
- `hederaUpdateTerc20StandaloneParams` (tgvalidatordHederaUpdateTERC20StandaloneParamsV2, optional) — Empty placeholders kept for shape symmetry. Add fields when the chain gains update support — that's a non-breaking change.
- `solanaUpdateNativeTokenParams` (tgvalidatordSolanaUpdateNativeTokenParamsV2, optional)
- `cantonUpdateNativeTokenParams` (tgvalidatordCantonUpdateNativeTokenParamsV2, optional)

### tgvalidatordImportAssetParamsV2

ImportAssetParamsV2 mirrors AssetParamsV2's shape for importing an existing on-chain asset.

- `hederaNativeTokenImportParams` (tgvalidatordHederaNativeTokenImportParamsV2, optional)
- `hederaTerc20StandaloneImportParams` (tgvalidatordHederaTERC20StandaloneImportParamsV2, optional)
- `solanaNativeTokenImportParams` (tgvalidatordSolanaNativeTokenImportParamsV2, optional)
- `cantonNativeTokenImportParams` (tgvalidatordCantonNativeTokenImportParamsV2, optional)

### tgvalidatordCantonNativeTokenParamsV2

- `instrumentID` (string, optional) — Unique on-chain identifier for the token. Used internally as the tokenID for asset whitelisting.
- `name` (string, optional) — Name used internally for asset whitelisting.
- `symbol` (string, optional) — Symbol used internally for asset whitelisting, usually the same as the instrumentID.

### tgvalidatordHederaUpdateNativeTokenParamsV2

- `name` (string, optional)
- `symbol` (string, optional)
- `expiry` (datetime, optional)
- `autoRenewPeriod` (string, optional)
- `memo` (string, optional)
- `metadata` (string, optional)

### tgvalidatordHederaUpdateTERC20StandaloneParamsV2

Empty placeholders kept for shape symmetry. Add fields when the chain gains update support — that's a non-breaking change.

### tgvalidatordSolanaUpdateNativeTokenParamsV2

### tgvalidatordCantonUpdateNativeTokenParamsV2

### tgvalidatordHederaNativeTokenImportParamsV2

### tgvalidatordHederaTERC20StandaloneImportParamsV2

### tgvalidatordSolanaNativeTokenImportParamsV2

### tgvalidatordCantonNativeTokenImportParamsV2

## Examples

**Request**

```json
{}
```

**Response**

```json
{
  "id": "string",
  "assetID": "string",
  "type": "ASSET_OPERATION_TYPE_V2_CREATE",
  "status": "ASSET_OPERATION_STATUS_V2_PENDING",
  "createdAt": "2024-01-15T09:30:00Z",
  "updatedAt": "2024-01-15T09:30:00Z",
  "initiatedByAddressID": "string",
  "failureReason": "ASSET_OPERATION_FAILURE_REASON_V2_UNKNOWN",
  "blockingReason": "ASSET_OPERATION_BLOCKING_REASON_V2_UNKNOWN",
  "create": {
    "label": "string",
    "price": "string",
    "decimals": "string",
    "params": {
      "cantonNativeTokenParams": {
        "instrumentID": "string",
        "name": "string",
        "symbol": "string"
      }
    },
    "blockchain": "string",
    "network": "string",
    "assetType": "string"
  },
  "update": {
    "label": "string",
    "price": "string",
    "params": {
      "hederaUpdateNativeTokenParams": {
        "name": "string",
        "symbol": "string",
        "expiry": "2024-01-15T09:30:00Z",
        "autoRenewPeriod": "string",
        "memo": "string",
        "metadata": "string"
      },
      "hederaUpdateTerc20StandaloneParams": {},
      "solanaUpdateNativeTokenParams": {},
      "cantonUpdateNativeTokenParams": {}
    }
  },
  "import": {
    "blockchain": "string",
    "network": "string",
    "label": "string",
    "price": "string",
    "decimals": "string",
    "address": "string",
    "params": {
      "hederaNativeTokenImportParams": {},
      "hederaTerc20StandaloneImportParams": {},
      "solanaNativeTokenImportParams": {},
      "cantonNativeTokenImportParams": {}
    }
  },
  "mint": {
    "destination": {
      "addressID": "string",
      "whitelistedAddressID": "string"
    },
    "amount": "string",
    "nftMetadata": [
      "string"
    ]
  },
  "burn": {
    "destination": {
      "addressID": "string",
      "whitelistedAddressID": "string"
    },
    "amount": "string",
    "nftTokenIDs": [
      "string"
    ]
  },
  "pause": {},
  "unpause": {},
  "pauseAccount": {
    "target": {
      "addressID": "string",
      "whitelistedAddressID": "string"
    }
  },
  "unpauseAccount": {
    "target": {
      "addressID": "string",
      "whitelistedAddressID": "string"
    }
  },
  "setKyc": {
    "target": {
      "addressID": "string",
      "whitelistedAddressID": "string"
    },
    "status": "KYC_STATUS_V2_APPROVED"
  }
}
```

**SDK Code**

```python
import requests

url = "https://your-protect-instance.example.com/api/rest/v2/assets/assetID/burn"

payload = {}
headers = {
    "Authorization": "Bearer <token>",
    "Content-Type": "application/json"
}

response = requests.post(url, json=payload, headers=headers)

print(response.json())
```

```javascript
const url = 'https://your-protect-instance.example.com/api/rest/v2/assets/assetID/burn';
const options = {
  method: 'POST',
  headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
  body: '{}'
};

try {
  const response = await fetch(url, options);
  const data = await response.json();
  console.log(data);
} catch (error) {
  console.error(error);
}
```

```go
package main

import (
	"fmt"
	"strings"
	"net/http"
	"io"
)

func main() {

	url := "https://your-protect-instance.example.com/api/rest/v2/assets/assetID/burn"

	payload := strings.NewReader("{}")

	req, _ := http.NewRequest("POST", url, payload)

	req.Header.Add("Authorization", "Bearer <token>")
	req.Header.Add("Content-Type", "application/json")

	res, _ := http.DefaultClient.Do(req)

	defer res.Body.Close()
	body, _ := io.ReadAll(res.Body)

	fmt.Println(res)
	fmt.Println(string(body))

}
```

```ruby
require 'uri'
require 'net/http'

url = URI("https://your-protect-instance.example.com/api/rest/v2/assets/assetID/burn")

http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true

request = Net::HTTP::Post.new(url)
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{}"

response = http.request(request)
puts response.read_body
```

```java
import com.mashape.unirest.http.HttpResponse;
import com.mashape.unirest.http.Unirest;

HttpResponse<String> response = Unirest.post("https://your-protect-instance.example.com/api/rest/v2/assets/assetID/burn")
  .header("Authorization", "Bearer <token>")
  .header("Content-Type", "application/json")
  .body("{}")
  .asString();
```

```php
<?php
require_once('vendor/autoload.php');

$client = new \GuzzleHttp\Client();

$response = $client->request('POST', 'https://your-protect-instance.example.com/api/rest/v2/assets/assetID/burn', [
  'body' => '{}',
  'headers' => [
    'Authorization' => 'Bearer <token>',
    'Content-Type' => 'application/json',
  ],
]);

echo $response->getBody();
```

```csharp
using RestSharp;

var client = new RestClient("https://your-protect-instance.example.com/api/rest/v2/assets/assetID/burn");
var request = new RestRequest(Method.POST);
request.AddHeader("Authorization", "Bearer <token>");
request.AddHeader("Content-Type", "application/json");
request.AddParameter("application/json", "{}", ParameterType.RequestBody);
IRestResponse response = client.Execute(request);
```

```swift
import Foundation

let headers = [
  "Authorization": "Bearer <token>",
  "Content-Type": "application/json"
]
let parameters = [] as [String : Any]

let postData = JSONSerialization.data(withJSONObject: parameters, options: [])

let request = NSMutableURLRequest(url: NSURL(string: "https://your-protect-instance.example.com/api/rest/v2/assets/assetID/burn")! as URL,
                                        cachePolicy: .useProtocolCachePolicy,
                                    timeoutInterval: 10.0)
request.httpMethod = "POST"
request.allHTTPHeaderFields = headers
request.httpBody = postData as Data

let session = URLSession.shared
let dataTask = session.dataTask(with: request as URLRequest, completionHandler: { (data, response, error) -> Void in
  if (error != nil) {
    print(error as Any)
  } else {
    let httpResponse = response as? HTTPURLResponse
    print(httpResponse)
  }
})

dataTask.resume()
```