# BitSafe Documentation

**Build with Bitcoin and decentralized applications on Canton Network.**

BitSafe documentation has two core product paths:

* **CBTC** for teams integrating Bitcoin into trading, custody, and application workflows on Canton Network
* **Decentralization Manager** for builders creating Decentralized Parties and governed applications on Canton Network

**Choose your path**

* **Build with Decentralization Manager**

  Launch governed applications, configure operators, and manage Decentralized Parties
* **Integrate CBTC**

  Mint, hold, transfer, and integrate CBTC into applications and services
* **Trade CBTC**

  Explore venue access, onboarding, and trading workflows
* **Understand the architecture**

  Learn how governance, privacy, and the security model fit together

<table data-view="cards"><thead><tr><th></th><th></th><th data-hidden data-card-target data-type="content-ref"></th><th data-hidden data-card-cover data-type="image">Cover image</th></tr></thead><tbody><tr><td><strong>Decentralization Manager</strong></td><td>Govern on-chain actions with Decentralized Parties. Architecture, setup, operations, and API reference.</td><td><a href="/pages/AG0Kxp23ErGc4ClTg6wB">/pages/AG0Kxp23ErGc4ClTg6wB</a></td><td><a href="/files/l3CQBQC0OxPLUXMbBxU7">/files/l3CQBQC0OxPLUXMbBxU7</a></td></tr><tr><td><strong>CBTC</strong></td><td>Understand CBTC's architecture, security model, operational guides, and user flows.</td><td><a href="/pages/HCdDtM6o2OOegBMsr28K">/pages/HCdDtM6o2OOegBMsr28K</a></td><td><a href="/files/hwBg0sJ1nU5QgdrCbdkN">/files/hwBg0sJ1nU5QgdrCbdkN</a></td></tr><tr><td><strong>Trading Firms</strong></td><td>Evaluate and onboard to CBTC. Strategies, venues, wallets, and compliance for trading firms.</td><td><a href="/pages/UaMq4TixqC0JHfe4C1g0">/pages/UaMq4TixqC0JHfe4C1g0</a></td><td><a href="/files/7Fd3LpDPCjP3U2qI45YG">/files/7Fd3LpDPCjP3U2qI45YG</a></td></tr><tr><td><strong>Developers</strong></td><td>Build apps, wallets, and DeFi protocols with CBTC on Canton. API reference, SDKs, and guides.</td><td><a href="/pages/aQEMkpPA3QtfNWrP0yoq">/pages/aQEMkpPA3QtfNWrP0yoq</a></td><td><a href="/files/JS1yBwsYcq1L9o2tPrwz">/files/JS1yBwsYcq1L9o2tPrwz</a></td></tr></tbody></table>

***

## Quick Links

**Product Suite**

* [System Overview](/product-suite/cbtc/system-overview/cbtc-token-standard-info) - How CBTC works on Canton
* [Security Model](/product-suite/cbtc/security-model/a-deep-dive-into-frost) - FROST signatures and decentralized custody
* [Operational Guides](/product-suite/cbtc/operational-guides) - Minting, price feeds, and swaps
* [User Flow](/product-suite/cbtc/user-flow) - End-to-end transaction lifecycle

**Trading Firms**

* [Why CBTC for Trading Firms](/trading-firms/why-cbtc-for-trading-firms) - Canton's edge for traders
* [Prop Desk Playbook](/trading-firms/prop-desk-playbook) - Rewards, strategies, and compliance
* [Getting Started](/trading-firms/getting-started-venues-wallets-and-cbtc-acquisition) - Venues, wallets, and CBTC acquisition
* [Onboarding Checklist](/trading-firms/onboarding-checklist-from-signup-to-first-trade) - From signup to first trade

**Developers**

* [Quick Start](/developers/cbtc-quick-start) - Mint your first CBTC in 15 minutes
* [API Reference](/developers/cbtc-api-reference) - Canton Ledger API endpoints
* [SDK Setup](/developers/sdk-setup-and-installation) - Install cbtc-lib and configure your environment
* [Minting and Burning](/developers/cbtc-minting-and-burning) - Convert BTC to CBTC with code
* [Decentralization Manager](/product-suite/decentralization-manager) - Govern on-chain actions with Decentralized Parties

**Decentralization Manager**

* [Architecture Overview](https://docs.bitsafe.finance/product-suite/decentralization-manager/architecture-overview) - System architecture, core concepts, and communication protocol
* [User Guide](https://docs.bitsafe.finance/product-suite/decentralization-manager/user-guide) - Walkthrough of the web UI for day-to-day operations
* [Custom DAML Templates](https://docs.bitsafe.finance/product-suite/decentralization-manager/custom-daml-templates) - Authoring and deploying your own governance templates
* [Use Cases](https://docs.bitsafe.finance/product-suite/decentralization-manager/use-cases) - Vault governance, FAR rewards, multi-sig wallet, and utility service
* [Contributing Guide](https://docs.bitsafe.finance/product-suite/decentralization-manager/contributing-guide) - Development setup, standards, and the PR process

***

> **Not sure where to start?** Browse the [Product Suite](/product-suite/cbtc) for a high-level understanding of CBTC, or check the [FAQs](/faqs) for quick answers. For trading firm enquiries, contact <sales@bitsafe.finance>.


# Product Suite

BitSafe builds infrastructure for institutions and developers operating on Canton Network.

## CBTC

CBTC is a 1:1 wrapped Bitcoin token on Canton Network, enabling private, institutional-grade yield, trading, and settlement with decentralized management and transparent custody.

## Decentralization Manager

Decentralization Manager is the open-source framework for creating and managing Decentralized Parties and governed applications.


# CBTC

CBTC is a 1:1 wrapped Bitcoin token by BitSafe, designed for secure and decentralized bridging to the Canton Network.

Each CBTC is CIP-56 compliant, and is fully backed by Bitcoin held in a secure, decentralized custody system powered by FROST (Flexible Round-Optimized Schnorr Threshold Signatures).

The wrapped token is issued by a decentralized threshold of parties on Canton, and is held non-custodially by the user.

This eliminates the risks associated with centralized custodians and traditional bridge architectures.

## How the Bitcoin Bridge works

The reserve capital for CBTC is held in a network of secure Bitcoin wallets, co-controlled by a decentralized network of Attestor nodes. This is not a traditional multisig wallet, but rather a sophisticated threshold signature operation.

Here's how it works:

**Decentralized Custody:** Instead of a single entity holding the private keys, the authority to spend the Bitcoin is distributed among a network of trusted, institutional-grade Attestor nodes. Each node holds a share of the private key, but no single node ever has access to the full key.

**Threshold Signatures with FROST:** To authorize a withdrawal, a threshold of Attestor nodes must collaboratively sign the transaction using the FROST protocol. This process generates a single, standard Schnorr signature that is indistinguishable from a regular Bitcoin transaction on-chain, enhancing privacy and reducing transaction fees.

**Taproot Native:** Using Bitcoin's Taproot upgrade allows any Bitcoin wallet that can send to a Taproot address (P2TR) to be used to deposit BTC and mint CBTC.

This model ensures that no single party - not even BitSafe - can unilaterally move the funds. The security of the system is based on the honest majority assumption of the Attestor network, which is composed of highly reputable and financially incentivized participants.

## Dual Network Security

BitSafe Attestors don't just manage Bitcoin - they also validate transactions on Canton. This means both your Bitcoin deposits and CBTC token creation are protected by the same trusted network, creating seamless security across both blockchains.

## Why Canton?

The CBTC-Canton integration advances institutional Bitcoin adoption by enabling scalable, privacy-preserving margin flows for structured products and derivatives. Canton has the following features:

* Configurable on-chain privacy settings: Flows are visible only to the counterparties who need to see them
* Built for lending, trading, and settlements

## Learn More

**For Trading Firms:** Strategies, onboarding, venue selection, and reward mechanics - see the [Trading Firms](/trading-firms) section.

**For Developers:** API reference, SDK setup, minting/burning workflows, and security deep dive - see the [Developers](/developers) section.

**Security:** For a detailed look at FROST threshold signatures and the Attestor network, see [A Deep-dive into FROST](/product-suite/cbtc/security-model/a-deep-dive-into-frost) or the [Security Deep Dive](/developers/security-deep-dive) in the Developers section.

**FAQs:** Common questions are answered in the [Trading Firms FAQ](/trading-firms/faq-for-trading-firms) and the [general FAQs](/faqs).

**Glossary and Resources:** See the [Trading Firms Glossary](/trading-firms/glossary) and [Resources](/trading-firms/resources), or the [Developer Resources](/developers/resources).

Help & feedback - reach us at <sales@bitsafe.finance> with questions.


# System Overview

## Architecture at a Glance

The CBTC system bridges the Bitcoin Layer‑1 UTXO model to Canton’s Daml‑based smart‑contract network. It operates through a coordinated, decentralized process to ensure every Bitcoin deposit is securely verified before minting CBTC

The bridge architecture consists of:

1. **Bitcoin Layer** - Bitcoin transactions are monitored and verified with required confirmations (currently 6)
2. **Attestor Network** - A decentralized network of Attestors monitor and manage Bitcoin deposit/withdrawal transactions, and translate them via a governance module on Canton to validate and execute actions
3. **Canton Asset Layer** - Daml contracts that mint and burn CBTC tokens, but only after a threshold of Attestor nodes contribute their Canton signatures to the contract execution. No CBTC can be minted or burned without this decentralized approval process For the full technical specification, see the CBTC Token Standard Info

## Core Actors & Roles

**Actor**

**Responsibilities**

**Coordinator**

Executes periodic checks every 60-120 seconds, monitors deposit accounts, constructs Bitcoin transactions, and submits governance actions

**Attestors**

Independent nodes that verify deposits/withdrawals and submit confirmations via Canton's governance module. Every important action requires group approval

**Minter**

Create deposit accounts, send Bitcoin to generated addresses, initiate withdrawals, and hold CBTC tokens

## Trust & Threat Model

The CBTC system relies on a decentralized network of Attestors who must coordinate via a governance module on Canton to validate and execute actions, and a group threshold signing process on the Bitcoin L1. Every important action requires group approval. This shared decision-making keeps CBTC decentralized, reliable, and secure

Because Canton provides deterministic finalityarrow-up-right, once a mint or burn is executed its state transition is irrevocably committed, removing the roll‑back risk that probabilistic Layer‑1s face

This ensures that no single party, including the Coordinator, can unilaterally mint CBTC or withdraw Bitcoin

## On-Ledger Governance Flow

The CBTC system relies on a decentralized network of Attestors who must coordinate via a governance module on Canton to validate and execute actions.

The governance process works as follows:

* For actions like **ConfirmDepositAction** (for minting) or **ArchiveWithdrawRequest** (for withdrawal finalization), each Attestor must submit their confirmation signature independently
* Each attestor member submits its signed confirmation message, and once a threshold of signatures has been reached on the contract, the Coordinator executes the action


# CBTC Token Standard Info

These values and the registry URLs are what allows any token standard compliant tool to integrate with CBTC.

API Reference: Token Standard API Docs

Requirements: CIP-56 compliant. No special requirements for holding CBTC.

## Devnet

Coordinator URL: <https://devnet.dlc.link/attestor-2>

## Testnet

Coordinator URL: <https://testnet.dlc.link/attestor-1>

## Mainnet

Coordinator URL: <https://mainnet.dlc.link/attestor-1>


# User Flow

User Flow

Mint Flow (Deposit BTC → Mint CBTC)

High‑Level Narrative

Minting converts BTC into CBTC on Canton in six coordinated steps.

From the user’s point of view the whole journey feels like a normal on‑chain deposit; the heavy lifting - vault creation, threshold signing, and contract issuance - happens behind the scenes.

Step‑by‑Step Walk‑through

1. **Authentication** - Users start by logging into their Canton account, establishing their on-chain identity for the deposit
2. **Request deposit address** - The system generates a unique Bitcoin address tied to the user's account. Power users can request multiple addresses for operational convenience, though a single address works for unlimited deposits.
3. **Send Bitcoin** - Users initiate a Bitcoin transaction to the provided address using any standard wallet - no special software or complex procedures required.
4. **Automated monitoring** - The bridge continuously scans the Bitcoin network for incoming transactions. Once your deposit reaches 6 confirmations (roughly 60 minutes), it enters the verification queue.
5. **Decentralized verification** - Multiple independent Attestor nodes review the confirmed transaction, each submitting their approval through Canton's governance system. This distributed verification prevents any single party from controlling the minting process.
6. **CBTC issuance** - When a threshold of Attestor approvals are gathered, the next periodic system check (every 60-120 seconds) triggers the minting of equivalent CBTC via the decentralized party model and the governance model. Timing & Finality

The minting and withdrawal processes are automated, requiring no manual coordination.

Burn Flow (Redeem CBTC → BTC)

High‑Level Narrative

Redeeming CBTC reverses the bridging process, unlocking native Bitcoin that backs your CBTC token balance.

From your perspective, it works like any crypto withdrawal - specify an amount and destination, then wait for Bitcoin to arrive in your wallet. The system handles the coordination between burning your CBTC tokens and releasing the underlying Bitcoin through decentralized Attestor approval.

Step‑by‑Step Walk‑through

1. **Authentication** - Sign into your Canton account to initiate the withdrawal process
2. **Set up withdrawal destinations** - Configure one or multiple Bitcoin addresses where you want to receive funds - your hardware wallet, exchange account, or any Bitcoin address you control. These addresses are stored for future withdrawals, making repeat transactions one-click simple.
3. **Submit withdrawal request** - Select how much CBTC to redeem and choose your destination address. Your CBTC tokens are immediately burned on Canton, ensuring they can't be double-spent, while your withdrawal enters the processing queue.
4. **Automated processing** - The system detects your pending withdrawal and constructs a Bitcoin transaction to your specified address. Multiple Attestors independently review and approve the transaction through Canton's governance system to burn the CBTC on Canton once the required threshold is reached.
5. **Bitcoin delivery** - Once Attestor approvals also reach the required threshold on the BTC L1, the fully-signed transaction is broadcast to the Bitcoin network. After standard confirmations (typically 6), your Bitcoin arrives at the destination address. Reliability & Safeguards

The withdrawal system includes multiple failure-resistant mechanisms:

* **Automatic retry logic** - If a Bitcoin transaction fails to broadcast initially, the system automatically detects the failure during subsequent checks and rebroadcasts using stored transaction data
* **Idempotent operations** - Each withdrawal generates a unique transaction ID that prevents accidental double-spending, even if network issues cause retry attempts
* **Distributed verification** - No single Attestor can block or manipulate withdrawals; the threshold approval system ensures continued operation even with some nodes offline


# Security Model

## FROST Threshold Signatures

CBTC uses FROST (Flexible Round-Optimized Schnorr Threshold Signatures) to secure Bitcoin deposits through a decentralized network of Attestor nodes. Unlike traditional on-chain multisig which requires multiple signatures and public keys, CBTC uses standard Bitcoin transactions with a single aggregated signature that is indistinguishable from regular Bitcoin transactions. This approach is compatible with any wallet that supports Taproot addresses and results in smaller transaction sizes, lower fees, and enhanced privacy compared to conventional multisig operations.

## Canton-Side Operations

Each BitSafe Attestor that helps sign Bitcoin transactions also operates a node on the Canton network. When creating new CBTC tokens, these Attestors must each approve the minting by submitting their agreement to the CBTC smart contract. Only when enough Attestors agree (reaching the threshold) are the new CBTC tokens actually minted.

## Canton Token Standard Compliance

CBTC uses the Canton registry utility and will adopt the universal token standard when viable

## Distributed Infrastructure

CBTC's security foundation rests on a carefully selected network of institutional-grade operators. The system employs 9 pre-screened external node operators (including established providers like P2P and Everstake) alongside 1 BitSafe-operated node.

Each operator maintains over $1 billion in AUM (Assets Under Management), ensuring they have both the technical expertise and financial incentives to maintain system integrity. These operators run both Bitcoin and Canton nodes.

## Cryptographic Address Generation

CBTC employs sophisticated cryptographic techniques to ensure each user receives a unique, secure Bitcoin deposit address. Each **DepositAccount** (DA) on Canton deterministically maps to a unique Bitcoin deposit address through a multi-step cryptographic process involving public key derivation and Taproot script construction.

**Two-Stage Derivation Process:**

1. **Entropy Generation:** The system starts with a fixed unspendable public key as the cryptographic foundation. Each DA's unique identifier undergoes SHA-256 hashing to generate entropy, which then serves as the chain code in the key derivation process. This creates a deterministic extended public key (xpub) that's unique to each deposit account.
2. **Taproot Integration:** The derived xpub combines with a fixed single-key script to construct a Taproot output with script-path spending enabled. This results in a valid P2TR (Pay-to-Taproot) Bitcoin address that's fully determined by the DA's identifier and can only be spent using the Attestors' group private key.

## Transaction Validation Rules

The system employs strict UTXO selection criteria to prevent double-spending and ensure proper transaction ordering:

**For Deposit Processing**: A UTXO qualifies for minting only if it received 6 confirmations after the DepositAccount's recorded block\_height, ensuring new deposits are processed in chronological order.

**For Withdrawal Processing**: A UTXO becomes eligible for spending only if it was confirmed with 6 confirmations before or at the DepositAccount's block\_height, guaranteeing that only properly secured funds can be withdrawn.

This dual-criteria approach creates a clear separation between "available for withdrawal" and "pending deposit" funds, preventing race conditions and ensuring the integrity of the 1:1 backing mechanism.


# A Deep-dive into FROST

Flexible Round-Optimized Schnorr Threshold (FROST) underpins the security and decentralization of the Bitcoin side of BitSafe CBTC. As a threshold signature scheme, FROST enables a group of participants to collectively generate a single Schnorr signature, without any single participant ever having access to the full private key.

This document provides a comprehensive technical overview of FROST, its integration with CBTC, and the significant advantages it offers for institutional Bitcoin custody.

## 1. Understanding FROST

### 1.1. What is FROST?

FROST is a threshold signature scheme that allows for the creation of Schnorr signatures from a distributed set of key shares.

### 1.2. Why FROST for CBTC?

The selection of FROST for decentralized control of the BTC in our on-chain Bitcoin network vault was a deliberate choice.

## 2. How FROST Works

### 2.1. Key Generation

FROST supports two primary methods: Trusted Dealer Generation and Distributed Key Generation (DKG).

### 2.2. The Signing Process

The FROST signing process is a two-round protocol coordinated by a designated entity.

### 2.3. Signature Aggregation and Verification

Once the Coordinator has received a threshold of valid signature shares, it can aggregate them into a single, final Schnorr signature.

## 3. Advanced Features and Security

### 3.1. Share Resharing and Revocation

One of the most powerful features of FROST is the ability to perform Verifiable Secret Resharing (VSR).

### 3.2. Security Model

The security of FROST is based on strong cryptographic assumptions.

## 4. FROST in CBTC: Implementation Details

### 4.1. Attestor Network Architecture

The CBTC system operates through a decentralized network of institutional-grade Attestors.

### 4.2. Coordinator and Governance Integration

The system employs a Coordinator that executes periodic checks every 60-120 seconds.

### 4.3. Threshold Signing Process

FROST enables the Attestor network to collectively authorize Bitcoin transactions.

### 4.4. Dual-Network Security Model

The CBTC system security relies on coordination between two networks.

## 5. More Reading

RFC 9591, Zcash Foundation FROST docs, Cryptology ePrint Archive Report 2020/852


# Operational Guides

The guides below provide high-level overviews for first-time users. Detailed technical implementation guides will be available as separate documents upon launch.

## Wallet Requirements

**Bitcoin side:** No special setup required - any wallet that can send BTC to a Taproot address (e.g., Sparrow, Ledger Live, BlueWallet) will work when you deposit into the bridge.

**For Canton:** Yes. After your Bitcoin is bridged, CBTC lives on Canton, so you'll need a wallet that understands Canton tokens. Today that list is short - the Canton CLI is fully supported, with additional wallets coming as the ecosystem progresses

## Run a Minter Application

A Minter Application enables institutions to offer CBTC deposit and withdrawal services to their users. As a Minter, you'll coordinate between Bitcoin deposits and Canton token issuance.

**Prerequisites**

* Minter Credential (Get yours herearrow-up-right)
* Bitcoin infrastructure for monitoring deposits and managing withdrawals
* Canton participant node for interacting with CBTC contracts
* Integration with the decentralized Attestor network for transaction approvals **High-Level Process**

Running a Minter Application involves monitoring Bitcoin addresses for user deposits, coordinating with Attestors for verification, and triggering CBTC minting on Canton. The bridge also handles the reverse process for withdrawals, burning CBTC tokens and facilitating Bitcoin payouts.

**Operational Considerations**

* Monitor Bitcoin network for deposit confirmations (6 blocks required)
* Coordinate with the governance module for Attestor approvals
* Manage periodic checks every 60-120 seconds for processing transactions

## Run an Attestor Node

Attestor Nodes form the decentralized security backbone of CBTC, independently verifying all mint and burn operations through Canton's governance system

**Prerequisites:**

* Technical infrastructure capable of running both Bitcoin and Canton nodes **High-Level Process**

Attestors monitor Bitcoin transactions, verify deposit and withdrawal requests, and submit confirmations through Canton's governance module. Each important action requires group approval, ensuring no single party can unilaterally control minting or burning.

**Operational Responsibilities**

* Independent verification of Bitcoin transactions reaching 6 confirmations
* Submission of **ConfirmDepositAction** for mints and **ArchiveWithdrawRequest** for burns
* Participation in the threshold approval process with other Attestors
* Maintenance of both Bitcoin monitoring and Canton governance infrastructure **Note:** Almost all of these responsibilities are automated with the only exception being governance (adding/removing nodes) which requires coordination between operators

## Spin Up a Canton Node/Instance

Running a Canton Node allows institutions to participate directly in the CBTC ecosystem, whether as holders, minters, or service providers

**Prerequisites:**

* Appropriate CBTC credential (Holder or Minter)
* Technical infrastructure for running Canton participant nodes
* Integration capabilities for connecting to the broader Canton network **High-Level Setup**

Canton nodes participate in the privacy-preserving, deterministic ledger that hosts CBTC contracts. Your node will process transactions, maintain contract state, and interact with other participants through Canton's encrypted messaging system.

**Key Components**

* Participant node for transaction processing and contract interaction
* Connection to Canton's sync domain for coordinated state updates
* Integration with CBTC governance contracts for credential verification
* API endpoints for application integration (if providing services to end users)


# Minting CBTC

This guide covers how to mint CBTC (Canton Bitcoin) by depositing native Bitcoin. CBTC is minted via the BitSafe Attestor Network, a decentralized network that monitors Bitcoin deposits and automatically mints CBTC to your Canton party. You do not need to run an attestor yourself.

## Integration Options

You can mint CBTC either through the BitSafe web application (no code required) or programmatically using the cbtc-lib Rust library.

* **Web Application:** Use the BitSafe app to initiate deposits and monitor minting status
* **cbtc-lib (Rust):** A library of helper functions for minting, burning, and transferring CBTC on Canton. See [cbtc-lib](https://github.com/DLC-link/cbtc-lib)

For full installation instructions, environment configuration, and code examples, see the [cbtc-lib README on GitHub](https://github.com/DLC-link/cbtc-lib).

## Prerequisites

* A Bitcoin wallet that supports Taproot (P2TR) addresses
* A Canton Network participant node
* Sufficient BTC for the deposit plus network fees
* A valid credential issued by your account manager
* For programmatic minting: the CBTC Minting App DAR files installed on your participant node. See the cbtc-lib Installation Guide

## Minting Flow

1. **Step 1: Create a Deposit Account** — Use the BitSafe app or `cbtc-lib`'s `mint_redeem::mint::create_deposit_account()` to create a deposit account. You will receive a unique BTC deposit address (Taproot/P2TR).
2. **Step 2: Send Bitcoin** — Send BTC to the provided deposit address from your Bitcoin wallet.
3. **Step 3: Wait for Confirmations** — The BitSafe Attestor Network monitors your deposit address and waits for 6+ Bitcoin block confirmations.
4. **Step 4: Automatic Minting** — Once confirmations are received, the attestor network verifies the deposit and automatically mints the equivalent CBTC to your Canton party. No action is required from you at this step.
5. **Step 5: Verify Balance** — Check your CBTC balance on your Canton participant node.

## Environment Configuration

Configure your environment to point to the correct BitSafe API:

| Environment | `BITSAFE_API_URL`                     |
| ----------- | ------------------------------------- |
| Devnet      | `https://api.devnet.bitsafe.finance`  |
| Testnet     | `https://api.testnet.bitsafe.finance` |
| Mainnet     | `https://api.mainnet.bitsafe.finance` |

## Developer Resources

* [cbtc-lib GitHub Repository](https://github.com/DLC-link/cbtc-lib)
* [CBTC Quick Start Guide](/developers/cbtc-quick-start)
* [CBTC Minting and Burning (Developer Reference)](/developers/cbtc-minting-and-burning)

## Important Notes

* Each CBTC is backed 1:1 by Bitcoin held in decentralized custody
* The minting process typically completes within minutes after 6 Bitcoin confirmations
* You do not need to run an attestor. The BitSafe Attestor Network handles all verification and minting automatically
* Deposits are subject to per-account limits - 0.0001 BTC minimum and 5 BTC maximum by default, adjustable on request. See [CBTC Minting and Burning](/developers/cbtc-minting-and-burning) for details


# Integrating BTC-USD Price Feed for CBTC

This guide explains how to integrate the BTC-USD price feed for CBTC applications on the Canton Network.

## Overview

Accurate and reliable price data is essential for DeFi applications using CBTC. This guide covers how to access and integrate the BTC-USD price feed within your Canton applications.

CBTC also has a Chainlink Proof of Reserve (CL PoR) feed for on-chain reserve verification: <https://data.chain.link/streams/cbtc-por-nav-datalink>

## Price Feed Architecture

The BTC-USD price feed for CBTC is designed to provide real-time, tamper-resistant pricing data that can be consumed by smart contracts and applications on the Canton Network.

## Integration Steps

### Step 1: Access the Price Feed

Connect to the price feed endpoint to receive real-time BTC-USD pricing data.

### Step 2: Validate the Data

Always validate the freshness and integrity of price data before using it in critical operations.

### Step 3: Implement in Your Application

Use the price feed data in your Canton application for operations such as collateral valuation, liquidation thresholds, and trading.

## Best Practices

* Always check the timestamp of price data to ensure freshness
* Implement fallback mechanisms in case of feed disruptions
* Use multiple price sources for critical operations


# Swap BTC to CBTC on Bron

A Step-by-Step Visual Guide To BTC/CBTC swaps on Bron

This guide walks you through swapping BTC to CBTC using the Bron platform.

## Overview

Bron provides a streamlined interface for swapping Bitcoin (BTC) to CBTC on the Canton Network. This guide covers the end-to-end process.

## Prerequisites

* A Bitcoin wallet with BTC
* A Canton Network wallet for receiving CBTC
* Access to the Bron platform

## Swap Process

### Step 1: Connect Your Wallets

Connect both your Bitcoin wallet and Canton wallet to the Bron platform.

### Step 2: Select the Swap Pair

Select BTC to CBTC as your swap pair. The platform will display the current exchange rate and any applicable fees.

### Step 3: Enter the Amount

Enter the amount of BTC you wish to swap to CBTC.

### Step 4: Review and Confirm

Review the transaction details including the amount, fees, and estimated completion time. Confirm the swap.

### Step 5: Complete the Transaction

Send the BTC to the provided address. Once confirmed on the Bitcoin network, your CBTC will be minted and sent to your Canton wallet.

## Fees and Timing

* Swap fees are displayed before confirmation
* Processing time depends on Bitcoin network confirmation speed
* CBTC is minted after sufficient Bitcoin confirmations


# Glossary

**Attestor** - Independent nodes that monitor Bitcoin, verify deposits and burns, and participate in the governance process to approve transactions.

**CBTC** - A 1:1 wrapped Bitcoin token built for secure trading and bridging on Canton.

**Burn** - The process of destroying CBTC tokens on Canton to initiate Bitcoin withdrawal.

**Coordinator** - The service that executes periodic checks, monitors deposits, and coordinates with Attestors.

**DepositAccount (DA)** - A Canton contract template that represents a deposit account, with each DA having a unique ID that deterministically maps to a Bitcoin deposit address.

**Mint** - The process of creating new CBTC tokens on Canton after confirmed Bitcoin deposits.

**Periodic Check (PC)** - A recurring process executed by the Coordinator every 60 to 120 seconds to trigger actions based on Bitcoin and Canton data.

**WithdrawAccount (WA)** - A Canton contract template representing a withdrawal account that stores a user-defined destination Bitcoin address.

**WithdrawRequest (WDR)** - A Canton contract template instantiated during withdrawal processing, containing the withdrawal amount, Bitcoin transaction ID, and destination address.


# Future Plans

The system has been designed to support future enhancements while maintaining the core mint-burn functionality described in this documentation.

Following are some ways to increase the functionality of CBTC:

* **Node operator rewards:** As a validator securing CBTC, you'll earn additional rewards from minting activity
* **Customer minting:** You can potentially mint CBTC on behalf of customers, earning Canton coin rewards to share with them
* **Utility-based rewards:** Canton is shifting toward rewarding apps that create actual trading and financial activity, which should benefit CBTC holders


# CBTC FAQs

## CBTC FAQs

## FAQs

#### What is CBTC?

CBTC is a wrapped Bitcoin (1:1 backed) on the Canton network, designed for institutional use cases. It's built by BitSafe (makers of iBTC) and will support liquidity provision, and integration with derivatives marketplaces (e.g., the Canton-QCP collaboration). It's privacy-enabled and secure, using Schnorr/FROST and Taproot-based signatures along with a decentralized network of Attestors for the bridge.

#### Do I need a Canton validator to participate?

Yes, you need to have a live validator and a validator address on Canton mainnet to receive credentials

#### What are the transaction fees?

Current transaction fees are 5 basis points for minting/burning and 3 basis points for transferring/locking/unlocking

#### Who operates the CBTC bridge nodes?

9 pre-screened external node operators (e.g., P2P, Everstake) with more than $1B in AUM and 1 BitSafe node, run both Bitcoin and Canton nodes

#### Do I need special wallets?

**Bitcoin side:** No special setup required - any wallet that can send BTC to a Taproot address (e.g., Sparrow, Ledger Live, BlueWallet) will work when you deposit into the bridge.

**For Canton:** Yes. After your Bitcoin is bridged, CBTC lives on Canton, so you’ll need a wallet that understands Canton tokens. Today that list is short - the Canton CLI is fully supported, with additional wallets coming as the ecosystem matures.

#### Are there any KYC/KYB requirements?

No additional KYC/KYB is required between app creators because acceptance into Canton requires sponsorship by a Supervalidator

#### Will running a CBTC Attestor Node make me a custodian of customer assets or allow me to sweep or transact against customer funds?

Running an Attestor Node does **NOT** make you a custodian of any CBTC assets Here's what Attestor Nodes actually do:

* Verify Bitcoin transactions and CBTC mint/burn operations
* Participate in Canton's governance system as a "signing party"
* Submit confirmations for deposits and withdrawals through automated processes
* Help maintain the decentralized security of the CBTC network What Attestor Nodes do **NOT** do:
* Hold or custody any CBTC tokens
* Store customer private keys
* Control any customer assets **The key distinction:** Attestors verify transactions; they don't custody assets. You can participate in the CBTC rewards system without any of the custodial concerns.

#### What future opportunities are available?

Following are some of the future opportunities with Canton and CBTC:

* **Node operator rewards:** As a validator securing CBTC, you'll earn additional rewards from minting activity
* **Customer minting:** You can potentially mint CBTC on behalf of customers, earning Canton coin rewards to share with them
* **Utility-based rewards:** Canton is shifting toward rewarding apps that create actual trading and financial activity, which should benefit CBTC holders

#### What if I have more questions?

Email <sales@bitsafe.finance> or join the community


# Audit Reports

* In August 2025, Quantstamp completed a security audit of CBTC's smart contracts on Canton Network. No High severity issues were found.


# Resources

## Resources

* FROST Whitepaper: <https://eprint.iacr.org/2020/852>
* Canton Whitepaper: <https://www.canton.network/whitepapers>


# CBTC Data & Price Feeds

This page covers where to find reserve data and price data for CBTC, and who to contact for access.

### Proof of Reserve

CBTC is backed 1:1 by Bitcoin, and that backing is verifiable on-chain through the Chainlink Proof of Reserve feed. The feed reports the reserves held against circulating CBTC and can be used for backing verification, monitoring, and risk checks.

* Chainlink CBTC PoR / NAV feed: <https://data.chain.link/streams/cbtc-por-nav-datalink>

### Price data

Kaiko provides a CBTC price feed built on Temple market data (the CBTC-USDCx pair). The pricing is served through Kaiko’s Fair Market Value endpoints available:

* On chain, through Kaiko’s [Pull Oracle](https://docs.kaiko.com/on-chain/kaiko-data/kaiko-reference-rates/data-on-ramp/canton-pull-oracle), which provides Kaiko-signed price quotes that can be verified and consumed within Canton workflows: <https://docs.kaiko.com/on-chain/kaiko-data/kaiko-reference-rates/data-on-ramp/canton-pull-oracle>
* Off chain, through Kaiko’s REST API: <https://docs.kaiko.com/rest-api/analytics-solutions/kaiko-fair-market-value/established-assets>\
  To get access to the Kaiko endpoint, reach out to the BitSafe team and we’ll make an introduction to Kaiko directly.

### BTC/USD as a reference price

Since CBTC is redeemable 1:1 for Bitcoin, a BTC/USD price feed remains a valid reference for integrations that don't yet need a dedicated CBTC feed.

See the existing guide on integrating a BTC/USD price feed for CBTC.


# Decentralization Manager

## Overview

Decentralization Manager is the open-source framework for creating and managing Decentralized Parties and governed applications on Canton Network.

It is currently in public beta.

Use it to coordinate operators, configure governance, and deploy application logic through the Generalized Governance Core, Token Management Module, and Custody Module.

Run it self-hosted, or use the BitSafe-hosted Admin UI where available.

## Features

* **Web-Based Management UI**: React frontend for managing decentralized parties
* **Multi-Party Onboarding**: Coordinated workflow for creating decentralized party namespaces
* **Contract Deployment**: Upload DAR files and deploy governance contracts with multi-party signing
* **Governance Actions**: View and manage governance confirmations with threshold-based execution
* **Participant Management**: View party membership, kick participants with threshold-based voting
* **OAuth Authentication (Keycloak or Auth0)**: Supports M2M (client\_credentials) and password flows for Ledger API access, with a per-node choice of provider for both frontend gating and outbound Canton tokens
* **Secure P2P Communication**: Noise Protocol Framework for encrypted coordinator to peer communication
* **Real-time Status**: Live peer connectivity monitoring and workflow progress tracking
* **Canton Integration**: Native gRPC integration with Canton Admin and Ledger APIs

## Documentation

* [Introduction](/product-suite/decentralization-manager/introduction): Start here - what Decentralization Manager does and why to decentralize your application on Canton
* [Architecture Overview](https://github.com/DLC-link/decentralization-manager/blob/main/docs/ARCHITECTURE.md): System architecture, core concepts, communication protocol, and technical constraints
* [User Guide](https://github.com/DLC-link/decentralization-manager/blob/main/USER_GUIDE.md): Walkthrough of the web UI for day-to-day party and governance operations
* [Custom DAML Templates](https://github.com/DLC-link/decentralization-manager/blob/main/docs/CUSTOM_DAML_TEMPLATES.md): Authoring and deploying your own DAML governance templates
* [Contributing Guide](https://github.com/DLC-link/decentralization-manager/blob/main/docs/CONTRIBUTING.md): Development setup, coding standards, commit conventions, and the PR process

### Security

The Decentralization Manager was audited by Quantstamp (May 2026). The full audit report is available here: [Quantstamp Audit Report](https://certificate.quantstamp.com/full/bitsafe-dec-manager/9d0b465f-46c1-41bc-8d56-cfb3d3c44a76/index.html)

## Architecture

The application runs as an HTTP server with an embedded React frontend. Multiple instances coordinate via the Noise Protocol:

* **Coordinator**: Initiates workflows and orchestrates multi-party operations
* **Peers**: Respond to coordinator commands, sign proposals, and execute local operations
* **Automatic Key Management**: Noise keypairs are generated automatically on first run

```
┌─────────────────┐ Noise Protocol ┌─────────────────┐
│ Participant 1 │◄───────────────────────►│ Participant 2 │
│ (Coordinator) │ │ (Peer) │
│ HTTP :8081 │ │ HTTP :8082 │
│ Noise :9001 │ │ Noise :9002 │
└────────┬────────┘ └────────┬────────┘
 │ │
 │ Canton Network │
 └───────────────────┬───────────────────────┘
 │
 ┌────────▼────────┐
 │ Canton Nodes │
 │ (Admin/Ledger │
 │ APIs) │
 └─────────────────┘
```

## Quick Start

### Prerequisites

* Rust toolchain (for building from source)
* Access to Canton participant nodes (Admin API and Ledger API)
* Docker (optional, for containerized deployment)

### Running Locally

```bash
# Build and run with env vars
DECPM_DIR=./development/participant-1 \
DECPM_PORT=8081 \
DECPM_CANTON_ADMIN_HOST=localhost \
DECPM_CANTON_ADMIN_PORT=5002 \
DECPM_CANTON_ADMIN_LEDGER_HOST=localhost \
DECPM_CANTON_LEDGER_PORT=5001 \
DECPM_NOISE_PORT=9001 \
cargo run -- serve

# Or with a .env file in the data directory
cargo run -- -d ./development/participant-1 serve

# Or with release build
cargo build --release
DECPM_PORT=8081 ./target/release/dec-party-manager -d ./development/participant-1 serve
```

Open [http://localhost:8081](http://localhost:8081/) in your browser.

### Running with Docker

```bash
# Build the image
docker build -t dec-party-manager .

# Run a single instance
docker run -p 8080:8080 -v ./data:/data \
 -e DECPM_CANTON_ADMIN_HOST=canton-node \
 -e DECPM_CANTON_ADMIN_PORT=5002 \
 -e DECPM_CANTON_LEDGER_HOST=canton-node \
 -e DECPM_CANTON_LEDGER_PORT=5001 \
 -e DECPM_NOISE_PORT=9001 \
 -e DECPM_CANTON_SYNCHRONIZER=global \
 -e DECPM_CANTON_NETWORK=devnet \
 dec-party-manager
```

### Running Multiple Participants (Development)

```bash
cd development
docker compose up
```

This starts three participant instances on ports 8081, 8082, and 8083.

## Configuration

All node configuration is done via environment variables (prefixed `DECPM_*`) or CLI arguments. The `--dir` (`-d`) flag points to a directory for persistent data. If a `.env` file exists in that directory, it is loaded automatically before parsing CLI arguments.

### Directory Structure

```
participant-dir/
├── .env # Optional environment file (loaded automatically)
└── data/
	├── noise.key # Auto-generated Noise keypair
	├── decpm.db # SQLite database (peers, party credentials)
	└── dars/ # DAR files for contract deployment
```

The database file path can be overridden with the `--db` CLI flag.

### Environment Variables

| Variable                         | Description                                                                                                                                         | Default                             |
| -------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------- | ----------------------------------- |
| `DECPM_DIR`                      | Root directory for persistent data (`--dir`/`-d`)                                                                                                   | .                                   |
| `DECPM_HOST`                     | Host address to bind the HTTP/UI server to                                                                                                          | `0.0.0.0`                           |
| `DECPM_PORT`                     | Port for the HTTP/UI server                                                                                                                         | `8080`                              |
| `DECPM_DB_PATH`                  | SQLite database path override (CLI flag `--db`)                                                                                                     | (defaults to `{dir}/data/decpm.db`) |
| `DECPM_DB_ENCRYPTION_KEY`        | Encryption key for secrets stored in the database                                                                                                   | (none)                              |
| `DECPM_ADMIN_ROLE`               | Role name that gates sensitive endpoints (unset skips the role check)                                                                               | (none)                              |
| `DECPM_ALLOWED_ORIGIN`           | Origin permitted by CORS (for example `https://dpm.example.com`)                                                                                    | (none, same-origin only)            |
| `DECPM_LISTEN_ADDRESS`           | Address to listen on for Noise protocol connections                                                                                                 | `0.0.0.0`                           |
| `DECPM_NOISE_PORT`               | Port for Noise protocol connections                                                                                                                 | `9000`                              |
| `DECPM_PUBLIC_ADDRESS`           | Public address that peers use to connect to this node                                                                                               | (falls back to listen address)      |
| `DECPM_CANTON_ADMIN_HOST`        | Canton Admin API host                                                                                                                               | `127.0.0.1`                         |
| `DECPM_CANTON_ADMIN_PORT`        | Canton Admin API port                                                                                                                               | `5002`                              |
| `DECPM_CANTON_LEDGER_HOST`       | Canton Ledger API host                                                                                                                              | `127.0.0.1`                         |
| `DECPM_CANTON_LEDGER_PORT`       | Canton Ledger API port                                                                                                                              | `5001`                              |
| `DECPM_CANTON_SYNCHRONIZER`      | Canton synchronizer name                                                                                                                            | `global`                            |
| `DECPM_CANTON_NETWORK`           | Canton network environment (`devnet`, `testnet`, `mainnet`)                                                                                         | `devnet`                            |
| `DECPM_KEYCLOAK_URL`             | Keycloak server URL for frontend auth                                                                                                               | (none)                              |
| `DECPM_KEYCLOAK_REALM`           | Keycloak realm name for frontend auth                                                                                                               | (none)                              |
| `DECPM_KEYCLOAK_CLIENT_ID`       | Keycloak client ID for frontend auth                                                                                                                | (none)                              |
| `DECPM_KEYCLOAK_INTERNAL_URL`    | Internal/backchannel Keycloak URL the server uses for OIDC discovery, JWKS, and introspection when it cannot reach the public Keycloak URL directly | DECPM\_KEYCLOAK\_URL                |
| `DECPM_AUTH0_DOMAIN`             | Auth0 tenant domain for frontend auth (mutually exclusive with the Keycloak variables)                                                              | (none)                              |
| `DECPM_AUTH0_CLIENT_ID`          | Auth0 SPA client ID for frontend auth                                                                                                               | (none)                              |
| `DECPM_AUTH0_AUDIENCE`           | Auth0 API audience the SPA's access tokens target                                                                                                   | (none)                              |
| `DECPM_TIMEOUT_HANDSHAKE`        | Noise handshake timeout in seconds                                                                                                                  | 30                                  |
| `DECPM_TIMEOUT_MESSAGE`          | Noise message timeout in seconds                                                                                                                    | 120                                 |
| `DECPM_TIMEOUT_RETRY_ATTEMPTS`   | Connection retry attempts                                                                                                                           | 3                                   |
| `DECPM_TIMEOUT_RETRY_DELAY`      | Connection retry delay in seconds                                                                                                                   | 5                                   |
| `DECPM_NOISE_RETRY_TIMEOUT_SEC`  | Per-attempt timeout for the bounded peer-Noise retry wrapper, in seconds                                                                            | 5                                   |
| `DECPM_NOISE_RETRY_MAX_ATTEMPTS` | Total attempts (initial plus retries) for the bounded peer-Noise retry wrapper                                                                      | 2                                   |
| `DECPM_NOISE_RETRY_BACKOFF_MS`   | Backoff between attempts of the bounded peer-Noise retry wrapper, in milliseconds                                                                   | 250                                 |

## API Reference

The manager exposes an HTTP API for configuration, workflow orchestration, and governance. A complete, interactive reference is available via the Swagger UI at /swagger-ui/ (OpenAPI document at /api-docs/openapi.json). Note that these interactive endpoints are only mounted in development and test builds; the shipped release image does not expose them. The main endpoint groups are:

* Node and network configuration: node and network info, peer list management, and per-party credential configuration.
* Decentralized parties: listing parties and viewing participant connectivity and key status.
* Workflows: starting, tracking, cancelling, retrying, and dismissing the onboarding, contracts, and kick workflows, plus managing invitations.
* Authentication: checking authentication status and testing outbound identity-provider auth per party.
* Governance: viewing governance state and confirmations, and submitting, executing, expiring, or cancelling governance actions.
* Contracts and services: querying deployed vaults, provider/user/registrar services, active contracts by template, configured package IDs, and token-standard contracts.
* DAR distribution: uploading DARs to the current node, distributing them across all participants, and tracking distribution progress.


# Introduction

Decentralization Manager is the open-source application for creating, configuring, and managing Decentralized Parties, and the governed applications that run on them.

A Decentralized Party is a single on-chain party whose keys and approvals are split across several independent node operators, so no single node can act alone. Understanding Decentralization Manager starts with understanding parties on Canton.

### Parties on Canton

On Canton Network, assets are held by a party, not by the contract itself. A party can be controlled by a single node, which means one operator holds the keys and can act alone. The Decentralized Party is native Canton technology that distributes control of a party across multiple independent nodes under a signing threshold, so an application no longer depends on, or has to trust, any single node.

### Single-party building concentrates risk

When one operator controls the party that holds an application's assets, several risks compound:

* **Custodial risk:** a single operator can move or freeze assets.
* **Operational risk:** if that one node goes offline, the application stops.
* **Counterparty risk:** users and partners place full trust in a single entity.
* **Regulatory risk:** sole control of user assets concentrates custodial responsibility in one operator.

Institutions ask two questions before committing capital: who can move or freeze these assets, and what happens if one operator goes down.

### Distributing trust makes applications institutional-grade

Decentralization Manager is the solution on Canton Network for building with Decentralized Parties and making applications institutional-grade. Decentralization Manager handles both sides: adding and removing operators, coordinating approvals, and keeping governance in sync. A party can be created, built upon, and configured from a visual interface or a CLI, and by connecting with peer operators, it runs the applications built on top of it.

### How Decentralization Manager works

Members propose an action, confirm it against a signing threshold, then execute, with keys and governance distributed across independent nodes by design.

<figure><img src="/files/lgCdzlmricCsvFgrREhk" alt=""><figcaption></figcaption></figure>

### What can be built

The same propose, confirm, execute lifecycle supports a wide range of applications:

* **Tokenization and real-world assets:** multi-party issuance with on-chain governance, no single signer on the asset.
* **Governed token issuance:** wrapped assets, stablecoins, and backed tokens issued and managed by a Decentralized Party.
* **Decentralized custody and wallets:** threshold-confirmed transfers with no single custodian counterparty.
* **DEXs, lending, and structured products:** governed parameters, treasury workflows, and admin operations on custom DAML.
* **Vaults:** pooled deposits under a curator, governed by a Decentralized Party.
* **Governed admin and protocol operations:** hold an application's most sensitive admin and governance actions, such as updating price oracles, adjusting supply caps, tuning interest rate formulae, and setting liquidation thresholds and borrowing limits, behind a signing threshold, so no single operator can change critical parameters alone. A protocol can decentralize these admin keys first, as a security operations baseline, before extending distribution to user-facing flows or to infrastructure resilience.

The rest of these docs cover product architecture, deploying Decentralization Manager on a Canton node, creating a Decentralized Party, onboarding node operators, and building with each module.


# Architecture Overview

System architecture, core concepts, communication protocol, and technical constraints.

The Decentralization Manager runs as an HTTP server with an embedded React frontend. Multiple instances coordinate with one another over the Noise Protocol Framework to perform multi-party operations on Canton network deployments.

## Core concepts

Coordinator: the instance that initiates workflows and orchestrates multi-party operations.

Peers: instances that respond to coordinator commands, sign proposals, and execute local operations.

Automatic key management: Noise keypairs are generated automatically on first run.

## Communication protocol

Instances communicate over the Noise Protocol Framework, which provides encrypted coordinator-to-peer messaging. The coordinator listens on a Noise port (default 9000) while serving the management UI over HTTP (default 8080). Peers are configured with each other's connection details, and the coordinator orchestrates key generation, topology proposals, multi-party signing, and submission to Canton.

## Technical constraints

Each node requires access to Canton participant nodes via the Admin API and Ledger API. Configuration is supplied through DECPM\_\* environment variables or CLI arguments. Peer and party state is persisted in a local SQLite database, and the interactive API reference (Swagger UI) is only mounted in development and test builds, not in the shipped release image.


# User Guide

Walkthrough of the web UI for day-to-day party and governance operations.

This guide walks through the day-to-day operations available in the Decentralization Manager web UI. Open the UI in your browser at the configured host and port (for example <http://localhost:8081>), authenticate via the configured identity provider, and use the workflows below.

## Creating a decentralized party (onboarding)

Configure every participant node with the others' connection details, start all participant servers, then on the coordinator's UI click Create Party and enter a party ID prefix. The coordinator invites peers and orchestrates cryptographic key generation, topology proposal creation, multi-party signing, and submission to Canton.

## Deploying contracts

From a party card, click Deploy Contracts, upload DAR files via the file picker, and configure the contract definitions (operator party, templates, fields). The coordinator distributes and uploads the DARs to all participants, prepares the ledger submission, collects multi-party signatures, and executes on the Canton ledger.

## Removing a participant (kick)

From a party card, click Kick Participant and select the participant to remove. The coordinator exports the current namespace state, creates updated topology proposals with a reduced threshold and the removed P2P mapping, collects signatures from the remaining members, and submits the proposal to Canton.

## Governance actions

The UI surfaces governance confirmations grouped by action. Members confirm a proposed action, and once the confirmation threshold is met the action can be executed. Stale confirmations can be expired or cancelled. Workflow instances and their lifecycle state are visible in the UI, where you can also dismiss or retry failed workflows.

## Monitoring status

Live peer connectivity monitoring and workflow progress tracking are available throughout the UI, so you can see which peers are reachable and how each multi-party workflow is progressing in real time.


# Custom DAML Templates

Authoring and deploying your own DAML governance templates.

The Decentralization Manager can deploy governance contracts built from your own DAML templates, in addition to the built-in token-custody, utility, and vote plugins. This page covers authoring custom templates and deploying them through the manager.

## Authoring templates

Write your governance logic as DAML templates and compile them into DAR files using the DAML SDK. Templates should define the operator party and any fields the manager will populate when configuring a contract definition. Keep template parameters explicit so they can be mapped to the deployment form in the web UI.

## Deploying templates

Deploy your compiled DAR files from a party card in the web UI by clicking Deploy Contracts and uploading the files. The coordinator distributes the DARs to all participants, prepares the ledger submission, collects multi-party signatures, and executes deployment on the Canton ledger. Configured package IDs for a party can be reviewed through the manager once deployment completes.

## Best practices

Test templates against a local development network before deploying to testnet or mainnet, version your DAR files so deployments are reproducible, and confirm that the operator party and signing thresholds in your template match the decentralized party configuration in the manager.


# Use Cases

Vault governance, FAR rewards, multi-sig wallet, and utility service walkthroughs.

The Decentralization Manager supports a range of multi-party governance scenarios on Canton. The walkthroughs below illustrate common deployments built on the onboarding, contract deployment, and governance workflows.

## Vault governance

Deploy vault contracts governed by a decentralized party, where actions on the vault require threshold-based confirmation from member participants before they execute on the ledger.

## FAR rewards

Coordinate the distribution of FAR rewards through governance confirmations, so that reward actions are proposed, confirmed by the required members, and executed under shared control.

## Multi-sig wallet

Operate a wallet under decentralized control, where transactions are signed by multiple participants and only execute once the configured signing threshold is reached, removing reliance on any single key holder.

## Utility service

Provision and run a utility service such as minting and burning under governance. The manager coordinates provider setup, mint, and burn actions through propose-confirm-execute cycles across the member participants.


# Contributing Guide

Development setup, coding standards, commit conventions, and the PR process.

Contributions to the Decentralization Manager are welcome. This guide covers setting up a development environment, the coding standards, commit conventions, and the pull request process. Please also review the project's Code of Conduct, and report any vulnerabilities via the Security Policy.

## Development setup

The backend is built with the Rust toolchain and the frontend is a React application embedded into the Rust binary at build time. Build with cargo build (add --release for a release build), and for the frontend run npm install and npm run dev for a hot-reloading development server, or npm run build for a production build.

```
# Build the backend (add --release for an optimized build)
cargo build

# Frontend (run from the frontend/ directory)
npm install
npm run dev    # hot-reloading dev server
npm run build  # production build
```

## Coding standards

Format Rust code with cargo fmt and lint with cargo clippy --all-targets --all-features -- -D warnings, which treats warnings as errors. Run cargo test for unit tests before opening a pull request.

```
# Format code
cargo fmt

# Lint (warnings treated as errors)
cargo clippy --all-targets --all-features -- -D warnings

# Run unit tests
cargo test
```

## Testing

The integration test boots a local Canton network, spawns three manager instances, configures peers, and runs an end-to-end governance workflow covering onboarding, DAR distribution, governance contract deployment, the plugin scenarios, and the kick workflow. Run it with ./integration-tests/run.sh, adding --verbose when diagnosing a stuck or failing run. The same suite can run against a real Canton devnet cluster with ./integration-tests/run.sh --target devnet.

```
# Run the integration test suite (quiet mode by default)
./integration-tests/run.sh

# Verbose mode when diagnosing a stuck or failing run
./integration-tests/run.sh --verbose

# Run against a real Canton devnet cluster
./integration-tests/run.sh --target devnet
```

## Commit conventions and pull requests

Follow the repository's commit message conventions and open a pull request for review. Ensure formatting, linting, and tests pass before requesting review, and keep changes focused so they are straightforward to review and merge.


# Use Cases

## Use Cases

This page outlines practical applications for CBTC, addressing specific needs for BitSafe's institutional and developer audiences.

### CBTC: Confidential Bitcoin on Canton Network

CBTC enables institutions to execute private trades and settlements on the Canton Network, ensuring transaction confidentiality for sensitive operations like OTC desk activities. It supports the creation of structured products, such as derivatives or margin flows, allowing investors to build complex financial instruments with privacy.

### Integrator Use Cases

DEX Liquidity: Decentralized exchanges can integrate CBTC to offer private Bitcoin trading pairs on Canton, enabling institutional participants to trade without exposing position sizes or strategies.

Wallet Support: Wallet providers can add CBTC support to give their institutional clients access to Canton Network's privacy features for Bitcoin holdings and transfers.

Custody and Vault Platforms: Third-party custody providers and vault platforms can integrate CBTC to offer their clients access to Canton's private settlement infrastructure while maintaining their existing custody workflows.

Trading Firm Settlement: Trading firms can use CBTC for confidential settlement of OTC trades, margin flows, and cross-venue transfers on Canton, reducing information leakage and counterparty risk.

### Key Benefits

* Tailored Strategies: From private settlement to complex derivatives, CBTC aligns with institutional operational needs.
* Transparency: Explicit risk disclosures, audited infrastructure, and real-time metrics empower informed decision-making.
* Flexibility: Self-custodial or regulated custody options cater to diverse compliance needs.


# FAQs

## FAQs

BitSafe is committed to supporting institutional investors and developers with clear answers and detailed resources. Below, we address common questions about CBTC, compliance, and security.

#### General Questions

How does BitSafe ensure compliance? BitSafe follows a compliance-first approach designed to support institutional onboarding and ongoing risk management. Contact BitSafe for current requirements and supported custody workflows for your jurisdiction.

What custody options are available? Investors can choose:

* Self-Custodial
* Regulated Custodians: Use trusted providers for CBTC
* Multi-Party Computation (MPC): Secure wallets for flexible, institutional-grade custody

#### Product-Specific Questions

CBTC

What privacy features does the Canton Network offer? Canton uses configurable sub-transaction privacy to ensure transaction details (e.g., amounts, parties) remain confidential, ideal for OTC desks and private trading. Only authorized nodes verify transactions.

How is CBTC secured? CBTC is secured by the Attestor Network, a decentralized group of independent, institutional-grade operators using FROST threshold signatures. No single entity controls the majority, and the system is designed so that no single party can unilaterally move funds.

What are the risks of bridging to CBTC? Risks include potential operator collusion (mitigated by the decentralized Attestor Network structure) and market risks on Canton. BitSafe provides explicit custody disclosures and audit reports for transparency.

#### Risk and Security

How does BitSafe mitigate smart contract vulnerabilities? BitSafe uses audited smart contracts from reputable developers, conducts regular third-party audits, and employs decentralized threshold security through the Attestor Network to minimize risks.

How are funds protected? Funds are safeguarded through:

* Decentralized Management: CBTC's Attestor Network prevents single-point failures
* Regulated Custody: Optional regulated custody for CBTC
* Audits: Regular smart contract and infrastructure audits ensure integrity

#### Support Channels

How can I get help?

* Commercial enquiries: <sales@bitsafe.finance>
* Technical support: <support@bitsafe.finance>


# Getting Oriented

### What this page is for

Use this page to quickly find the right section of the docs site for what you are trying to do.

### I am new here. Where should I start?

* If you are integrating CBTC into an app, start in **Developers** and begin with **CBTC Quick Start**.
* If you are a trading firm evaluating or onboarding, start in **Trading Firms**.

### Key links

* Developers
* CBTC Quick Start: <https://docs.bitsafe.finance/developers/cbtc-quick-start>
* API Reference: <https://docs.bitsafe.finance/developers/cbtc-api-reference>
* Authentication: <https://docs.bitsafe.finance/developers/cbtc-authentication>
* Trading Firms
* Overview: <https://docs.bitsafe.finance/trading-firms>
* Getting Started: <https://docs.bitsafe.finance/trading-firms/getting-started-venues-wallets-and-cbtc-acquisition>
* FAQ for Trading Firms: <https://docs.bitsafe.finance/trading-firms/faq-for-trading-firms>
* CBTC (Product Suite)
* CBTC FAQs: <https://docs.bitsafe.finance/product-suite/cbtc/cbtc-faqs>
* Audit Reports: <https://docs.bitsafe.finance/product-suite/cbtc/audit-reports>

### What is CBTC?

CBTC is a 1:1 wrapped Bitcoin token by BitSafe that lives on the Canton Network.

### What is BitSafe?

BitSafe builds institutional-grade Bitcoin infrastructure and products. CBTC is BitSafe’s Bitcoin product on the Canton Network.


# CBTC Basics

### What this page is for

This page answers the most common cross-cutting questions about CBTC. For deeper content, follow the links in each answer.

### How do I acquire CBTC?

If you are a trading firm, start here:

* <https://docs.bitsafe.finance/trading-firms/getting-started-venues-wallets-and-cbtc-acquisition> If you are integrating minting into an application, start here:
* <https://docs.bitsafe.finance/developers/cbtc-quick-start>

### How do minting and burning work?

For the full lifecycle and edge cases, see:

* <https://docs.bitsafe.finance/developers/cbtc-minting-and-burning>

### Do I need to run a Canton validator node?

It depends on your workflow. Some acquisition paths do not require running a node, but direct minting flows typically do. Start with:

* <https://docs.bitsafe.finance/trading-firms/getting-started-venues-wallets-and-cbtc-acquisition>

### Is there a testnet?

Yes. Start with:

* <https://docs.bitsafe.finance/developers/cbtc-testnet-guide>

### Where can I find definitions of common terms?

* <https://docs.bitsafe.finance/product-suite/cbtc/glossary>
* <https://docs.bitsafe.finance/trading-firms/glossary>


# Security and Audits

### What this page is for

This page covers the most common security questions at a high level and points to the canonical pages for details.

### How is CBTC secured?

CBTC uses threshold signing with FROST to secure Bitcoin reserves. For the detailed security explanation, see:

* <https://docs.bitsafe.finance/developers/security-deep-dive>

### Is CBTC audited?

See the audit reports here:

* <https://docs.bitsafe.finance/product-suite/cbtc/audit-reports> You can also view the public audit report here:
* <https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html>

### Where can I learn more about the security model?

* <https://docs.bitsafe.finance/product-suite/cbtc/security-model>

### What are the main things to double-check before production use?

* Use the Developers docs as the source of truth for integration steps.
* Treat API behavior as subject to change unless explicitly labeled otherwise.
* Validate assumptions against the changelog for recent updates: <https://docs.bitsafe.finance/developers/changelog>


# Support

### What this page is for

Use this page to figure out the fastest path to help.

### Sales and onboarding

If you are evaluating CBTC as a trading firm, want access, or need introductions to venues and partners, use:

* Email: <sales@bitsafe.finance>
* Trading Firms overview: <https://docs.bitsafe.finance/trading-firms>
* Trading Firms FAQ: <https://docs.bitsafe.finance/trading-firms/faq-for-trading-firms>

### Technical support for developers

If you are integrating CBTC and need help with authentication, APIs, minting, burning, or testnet:

* Email: <support@bitsafe.finance>
* Start here: <https://docs.bitsafe.finance/developers>

### Reporting a docs issue

Email the most relevant address above with:

* The page URL
* The exact sentence or section that looks wrong
* What you expected to see instead


# Brand & Press

For press inquiries or branding details, refer to our [Branding Kit](https://bitsafe.finance/brand-kit) or reach out to us at <sales@bitsafe.finance>.


# Trading Firms

Evaluate and onboard to CBTC as a trading firm. Find venue guides, reward playbooks, onboarding checklists, and everything you need to start trading institutional-grade Bitcoin on the Canton Network.


# Overview

Trade CBTC on Canton with privacy, MEV protection, and decentralized custody on top of your trading P\&L.

***

## For Prop Trading Desks

> ⚡ Whether you're running market making, arbitrage, or inventory rebalancing strategies, Canton's transaction-count-based rewards mean your existing edge in execution speed and trade frequency translates directly into Canton Coin rewards on top of your P\&L.
>
> * **Prop Desk Playbook** - Strategies and reward mechanics
> * **Selecting a Trading Venue** - Compare RFQ, CLOB, and AMM options

***

> 💰
>
> #### Passive Yield
>
> Not running an active desk? SciFeCap SMA offers a fully managed option targeting 8-10% yield with no infrastructure required on your side. 🔍
>
> #### Evaluating CBTC?
>
> Start with **Why CBTC for Trading Firms** for Canton's differentiators, then check the **FAQ** for common questions from trading firms.

***

> 💡 **Trade BTC with privacy, MEV protection, and institutional infrastructure →** Start with the [Prop Desk Playbook](https://docs.bitsafe.finance/trading-firms/prop-desk-playbook) for strategies and reward mechanics, then use [Getting Started: Venues, Wallets, and CBTC Acquisition](https://docs.bitsafe.finance/trading-firms/getting-started-venues-wallets-and-cbtc-acquisition) to find the right fit for your desk.


# Why CBTC for Trading Firms

CBTC is the native wrapped Bitcoin on the Canton Network, designed for institutional trading with privacy, MEV protection, and decentralized custody. This page explains why trading firms are integrating CBTC into their operations.

***

## Canton's Differentiators for Traders

| **🛡️ MEV Protection**                                   | **🔒 Private Positions**                                           | **🏛️ Institutional Counterparties**                                      |
| -------------------------------------------------------- | ------------------------------------------------------------------ | ------------------------------------------------------------------------- |
| No public mempool. No front-running or sandwich attacks. | Your positions and strategy are not visible to other participants. | All nodes are KYC-verified. Trade against vetted, compliant institutions. |

***

## How CBTC Is Secured

CBTC uses **FROST threshold signatures** over Bitcoin UTXOs for decentralized custody. There is no single custodian holding the underlying BTC.

* **1:1 BTC backing** at all times, verified by Chainlink Proof of Reserve
* **Decentralized Attestor Network** collectively approves mints and burns using a 2-of-4 threshold signing scheme
* **No single point of failure.** No individual entity can unilaterally move the underlying Bitcoin
* **Audited by Quantstamp.** Full report available at [certificate.quantstamp.com](https://certificate.quantstamp.com/)

***

## How to Trade CBTC

> #### Active Trading
>
> For firms with in-house quant and dev resources running spot BTC strategies.
>
> * Market making, arbitrage, inventory rebalancing, directional trading
> * Multiple venue types: RFQ, CLOB, AMM
> * Transaction-count-based rewards favor high-frequency strategies See the **Prop Desk Playbook** for strategy details.

***

## Use Cases

> 📈 **Spot and Perpetual Trading** Trade across RFQ (Elk/Trngle), CLOB (Temple Digital), and AMM (Tradefast) venues. No platform fees on most venues currently. 📊 **Lending and Borrowing** Lend CBTC on Haven Digital, Acme Markets, or Verity. Earn yield from interest on every lending transaction. Over-collateralized and smart contract secured. 💎 **Collateral Management** Use CBTC as high-quality collateral across multiple Canton venues. Atomic settlement reduces counterparty risk and improves capital efficiency. 🏗️ **Structured Products** Combine derivatives, lending, and spot markets to build risk-managed structured products. Canton's privacy model keeps your strategies confidential.

***

## Recommended Trading Pairs

| **Pair**          | **Description**                        | **Notes**                                         |
| ----------------- | -------------------------------------- | ------------------------------------------------- |
| **CBTC / USDXLR** | Canton-native yield-bearing stablecoin | Primary pair. Earns rewards from both assets.     |
| **CBTC / USDCx**  | Cross-chain stablecoin                 | Familiar stable pairing for BTC traders.          |
| **CBTC / CC**     | Canton Coin                            | Network token exposure. Available on most venues. |

Pair availability varies by venue. See **Selecting a Trading Venue** for venue-specific details.

***

## Technical Resources

* [CBTC Technical Documentation](https://docs.bitsafe.finance/product-suite/cbtc)
* [FROST Whitepaper](https://eprint.iacr.org/2020/852) (threshold signature security model)
* [Canton Network Whitepaper](https://www.canton.network/whitepapers)
* [Quantstamp Audit Report](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html)

***

## Next Steps

> 📝 **Ready to get started?**
>
> * Read the **Prop Desk Playbook** to understand strategies and reward mechanics
> * Compare venues in **Selecting a Trading Venue**
> * Follow the **Onboarding Checklist** to go from signup to first trade
> * [Complete the CBTC Signup Form](https://bitsafe.typeform.com/to/NsiwLKIY)
> * Email: <sales@bitsafe.finance>

***

> ℹ️ **Disclosures** Target yields are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Strategies carry risk; conduct independent due diligence. This is not investment advice.


# Prop Desk Playbook

This guide is for prop trading firms with in-house quant and dev resources running spot BTC strategies. It explains how Canton's reward model works, which strategies generate the most value, and what rules apply.

***

## How Canton's Reward Model Works for Active Traders

Canton Network rewards are based on **transaction count, not volume.** Every legitimate transaction involving CBTC generates Canton Coin (CC) rewards. For firms already running high-frequency spot strategies, this means your existing edge in execution speed and trade frequency translates directly into CC rewards on top of your trading P\&L.

* No minimum volume thresholds. Every accepted trade counts. Rewards are only generated on transactions accepted by the counterparty.
* Strategies you already run (market making, arbitrage, inventory rebalancing) generate both trading P\&L *and* network rewards.

***

## Strategies That Work

Canton's reward model rewards *frequency of legitimate economic activity.* These strategies naturally align with how prop firms already operate.

### Market Making

Quote CBTC/USDXLR or CBTC/USDCx with defined inventory bands. Earn spread P\&L plus Canton rewards on every fill.

### Cross-Venue Arbitrage

Exploit pricing differences between Elk RFQ, Temple CLOB, and Tradefast AMM. Each leg generates a separate reward-eligible transaction.

### Inventory Rebalancing

Rotate CBTC across venues and pairs as part of normal risk management. Every rebalance trade counts toward rewards.

### Directional Spot Trading

Apply existing spot BTC strategies to CBTC pairs. Same directional thesis, additional reward layer.

### Basis Trading

Trade CBTC vs BTC price differentials across Canton and external venues.

***

## Venue Selection for Prop Desks

Canton supports multiple venue types. The right choice depends on your trading style, technical stack, and preferred execution model.

### Which venue fits your desk?

**Do you need institutional-size execution with custom pairs?**

* **Elk / Trngle RFQ:** Programmatic OTC, negotiable spreads, bring your own wallet **Do you want an exchange-style order book with the best reward economics?**
* **Temple Digital CLOB:** 40% bonus reward share on top of standard CBTC rewards **Do you want fast deployment with familiar DeFi infrastructure?**
* **Tradefast AMM:** Uniswap V2 style, fastest integration path **Want the simplest starting point to test the waters?**
* **Bron:** Intuitive interface, comprehensive docs, quick onboarding For full venue comparison tables and integration details, see **Selecting a Trading Venue**.

***

## Anti-Gaming Rules

> ⚠️ **Important:** Strategies must involve real economic risk. Canton's tokenomics accountability process flags and shuts down scripted back-and-forth transfers (A to B to A) designed solely to farm rewards. If your strategy does not involve swapping into another asset, managing inventory risk, or providing liquidity, it will likely be flagged. Legitimate activity includes: market making, arbitrage, inventory rebalancing, directional trading, lending, and liquidity provision.

***

## Getting Started

> 📝 **Ready to start?**
>
> 1. Compare venues in **Selecting a Trading Venue**
>
> 2. Follow the **Onboarding Checklist** from signup to first trade
>
> * [Complete the CBTC Signup Form](https://bitsafe.typeform.com/to/NsiwLKIY)
> * Email: <sales@bitsafe.finance>

***

> ℹ️ **Disclosures** Target yields are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Strategies carry risk; conduct independent due diligence. This is not investment advice.


# Getting Started: Venues, Wallets, and CBTC Acquisition

Canton supports multiple venue types for trading CBTC, each with different execution models, fee structures, and reward economics. This guide helps you choose the right venue for your firm.

***

> ### Choose Your Venue
>
> **Do you have in-house quant and dev resources?**
>
> * **Yes:** You're a fit for active trading. See the venue comparison below.
> * **No:** Consider **Temple Digital LP** (passive, single-sided) or **SciFeCap SMA** (fully managed, 8-10% target yield). **Do you need institutional-size execution with custom pairs?**
> * **Elk / Trngle RFQ.** Contact Elk Capital for spread negotiation based on expected volume. **Do you want an exchange-style order book with the best reward economics?**
> * **Temple Digital CLOB.** 40% bonus reward share on top of standard CBTC rewards. **Do you want fast deployment with familiar DeFi infrastructure?**
> * **Tradefast AMM.** Uniswap V2 style, fastest integration path. **Want the simplest starting point?**
> * **Bron.** Intuitive interface, comprehensive docs, quick onboarding.

***

## Active Trading Venues

For firms with in-house quant and dev resources running active strategies.

| **Venue**          | **Type**     | **Best For**                 | **Key Features**                                                          | **Pairs**                   |
| ------------------ | ------------ | ---------------------------- | ------------------------------------------------------------------------- | --------------------------- |
| **Elk / Trngle**   | RFQ          | Institutional-size execution | Programmatic OTC, negotiable spreads, custom pairs, bring your own wallet | Multiple (custom available) |
| **Temple Digital** | CLOB         | Order book traders           | Exchange-style order book, 40% bonus reward share, best reward economics  | CC-CBTC, USDCx-CBTC         |
| **Tradefast**      | AMM          | Fast deployment              | Uniswap V2 style, fastest integration path, familiar DeFi infrastructure  | BTC-CBTC, USDCx-CBTC        |
| **Bron**           | Wallet + DEX | Simple starting point        | Intuitive interface, comprehensive docs, quick onboarding                 | BTC-CBTC, CC-CBTC           |

***

## Passive Allocation Options

For firms seeking yield without active management or infrastructure build-out.

| **Option**            | **Type**            | **Description**                                 | **Key Details**                                                   |
| --------------------- | ------------------- | ----------------------------------------------- | ----------------------------------------------------------------- |
| **Temple Digital LP** | Liquidity Provision | Single-sided liquidity with no impermanent loss | Deposit CBTC, earn trading fees and Canton Coin rewards           |
| **SciFeCap SMA**      | Managed Account     | Fully managed strategy with 8-10% target yield  | No active management required. Professional portfolio management. |

> ℹ️ Target yields for passive options are illustrative only. Actual returns depend on market conditions, network activity, and token economics.

***

## Recommended Trading Pairs

| **Pair**          | **Description**                        | **Notes**                                     |
| ----------------- | -------------------------------------- | --------------------------------------------- |
| **CBTC / USDXLR** | Canton-native yield-bearing stablecoin | Primary pair. Earns rewards from both assets. |
| **CBTC / USDCx**  | Cross-chain stablecoin                 | Familiar stable pairing for BTC traders.      |
| **CBTC / CC**     | Canton Coin                            | Network token exposure.                       |

Pair availability varies by venue. Check the active trading venues table above for venue-specific pairs.

***

## Canton Wallet Options

You need a Canton-compatible wallet to hold and transact with CBTC.

| **Wallet**  | **Type**           | **Best For**                                       |
| ----------- | ------------------ | -------------------------------------------------- |
| **Zoro**    | Self-custody       | Firms wanting SDK/API access and full control      |
| **Console** | Self-custody       | Browser-based with clear signing and risk checks   |
| **Loop**    | Self-custody       | Web-based, no extensions needed, open source SDK   |
| **Cantor8** | Enterprise custody | Multi-signature security and regulatory compliance |

For the full list of wallets and DeFi apps, see the **Canton DeFi Ecosystem** page.

***

## Acquiring CBTC

Two paths depending on your infrastructure:

**Option A: OTC Purchase** *(fastest, no Canton node required)*

* Initiate a cross-chain CBTC swap with Trngle or an OTC purchase through Elk Capital
* Ideal for firms without a Canton validator node
* Contact Elk Capital for spread negotiation based on expected volume **Option B: Direct Minting** *(requires Canton validator node)*
* Call Rust APIs via cbtc-lib to mint CBTC directly from BTC
* More cost-effective for high-volume operations
* See the developer documentation at [docs.bitsafe.finance/product-suite/cbtc](https://docs.bitsafe.finance/product-suite/cbtc) for technical details

***

## Don't Have a Canton Validator Node?

> ℹ️ **Multi-tenant validators** provide a streamlined, cost-effective path to network participation without running a full Canton validator. BitSafe can connect you with trusted providers in the ecosystem.
>
> * Lower barrier to entry
> * Shared infrastructure costs
> * Get started in days, not weeks

***

## Next Steps

> 📝 **Ready to choose a venue?**
>
> * Review the **Prop Desk Playbook** for strategy recommendations
> * Follow the **Onboarding Checklist** to go from signup to first trade
> * [Complete the CBTC Signup Form](https://bitsafe.typeform.com/to/NsiwLKIY)
> * Email: <sales@bitsafe.finance>

***

> ℹ️ **Disclosures** Target yields are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Strategies carry risk; conduct independent due diligence. This is not investment advice.


# Canton DeFi Ecosystem

The Canton Network ecosystem is growing rapidly with new wallets, DEXes, and DeFi applications launching regularly. This guide helps you navigate the available options for interacting with Canton Network and CBTC.

> Each venue and wallet maintains its own documentation and onboarding process. For introductions or access requests, contact <sales@bitsafe.finance>.

***

## Wallets

Store, send, receive, and manage your Canton assets.

| **Wallet**      | **Type**           | **Description**                                                                | **Website**                                   |
| --------------- | ------------------ | ------------------------------------------------------------------------------ | --------------------------------------------- |
| **Zoro**        | Self-custody       | SDK and API support for institutional traders                                  | [zorowallet.com](https://zorowallet.com/)     |
| **Console**     | Self-custody       | Browser wallet with clear signing and built-in risk checks                     | [consolewallet.io](https://consolewallet.io/) |
| **Loop**        | Self-custody       | Web-based, works in any browser, no extensions needed. Open source SDK.        | [cantonloop.com](https://cantonloop.com/)     |
| **Cantor8**     | Enterprise custody | Privacy-first mobile wallet. No registration, no data collection.              | [cantor8.tech](https://cantor8.tech/)         |
| **Bron**        | Self-custody       | Seedless recovery with MPC security, plus cross-chain swaps and staking        | [bron.org](https://bron.org/)                 |
| **Cansai**      | Self-custody       | First iOS-native Canton wallet with seamless Apple device sync                 | [cansai.app](https://cansai.app/)             |
| **Cypherock**   | Hardware           | Hardware wallet with decentralized key management                              | [cypherock.com](https://cypherock.com/)       |
| **Nightly**     | Multi-chain        | Multi-chain wallet with Canton support                                         | [nightly.app](https://nightly.app/)           |
| **Send Wallet** | Self-custody       | Passkey-first wallet. Log in with face or fingerprint instead of seed phrases. | [cantonwallet.com](https://cantonwallet.com/) |

***

## Trading Venues

Swap, trade, and provide liquidity on Canton.

| **Venue**          | **Type**     | **Available Pairs**         | **Website**                               |
| ------------------ | ------------ | --------------------------- | ----------------------------------------- |
| **Elk / Trngle**   | RFQ          | Multiple (custom available) | [trngle.xyz](https://trngle.xyz/)         |
| **Temple Digital** | CLOB         | CC-CBTC, USDCx-CBTC         | [temple.digital](https://temple.digital/) |
| **Tradefast**      | DEX / AMM    | BTC-CBTC, USDCx-CBTC        | [trade.fast](https://trade.fast/)         |
| **Bron**           | Wallet + DEX | BTC-CBTC, CC-CBTC           | [bron.org](https://bron.org/)             |
| **TradeCraft**     | AMM          | CC-CBTC                     | [tradecraft.fi](https://tradecraft.fi/)   |
| **Cantex**         | DEX          | Multiple pairs              | [cantex.io](https://cantex.io/)           |
| **Kairo**          | DEX          | Multiple pairs              | [kairo.ag](https://kairo.ag/)             |

***

## Lending Platforms

Borrow and lend on Canton.

| **Platform**               | **Status**  | **Description**                                                           | **Website**                                                       |
| -------------------------- | ----------- | ------------------------------------------------------------------------- | ----------------------------------------------------------------- |
| **Haven Digital Partners** | Live        | Institutional lending app on Canton                                       | [canton-lending.havendp.com](https://canton-lending.havendp.com/) |
| **Acme (Hello Moon)**      | Live        | Decentralized, overcollateralized lending pools / money markets on Canton | [acmemarkets.cc](https://acmemarkets.cc/)                         |
| **Verity (Hashrupt)**      | Live        | On-chain collateralized lending and loan lifecycle management on Canton   | [hashrupt.com](https://hashrupt.com/)                             |
| **Holdex**                 | In progress | Lending platform being built on Canton                                    | [holdex.io](https://holdex.io/)                                   |

***

## Other DeFi Apps

Asset management, prediction markets, and more on Canton.

| **App**      | **Category**      | **Website**                                 |
| ------------ | ----------------- | ------------------------------------------- |
| **Unhedged** | Prediction Market | [unhedged.gg](https://unhedged.gg/)         |
| **Modulo**   | DeFi Platform     | [modulo.finance](https://modulo.finance/)   |
| **AllDeFi**  | Asset Management  | [alldefi.finance](https://alldefi.finance/) |
| **Hecto**    | DeFi Platform     | [hecto.finance](https://hecto.finance/)     |

***

## Coming Soon

* **Additional Wallets:** Utila, Meteor Wallet

***

*This is a living document. The Canton Network ecosystem is evolving rapidly. Check back regularly for updates.*

***

> ℹ️ **Disclosures** This is not investment advice. Conduct independent due diligence before interacting with any third-party application.


# Onboarding Checklist: From Signup to First Trade

This guide walks you through the complete onboarding process for trading CBTC on Canton, from initial signup to your first live trade. Expected timeline: 1 to 2 weeks depending on your firm's readiness and chosen venue.

***

## Step 1: Express Interest

> **Complete the CBTC Signup Form** [bitsafe.typeform.com/to/NsiwLKIY](https://bitsafe.typeform.com/to/NsiwLKIY) This registers your firm's interest and triggers outreach from the BitSafe BD team. You will be contacted to discuss your trading goals, preferred venues, and technical requirements.

***

## Step 2: Execute Agreements

> **Sign the MSA**
>
> * **Master Service Agreement (MSA):** Standard commercial terms for using BitSafe services
> * **KYC/AML:** Complete any required compliance checks Contact <sales@bitsafe.finance> if you have questions about the agreements.

***

## Step 3: Set Up a Canton Wallet

> **Choose and configure your wallet** You need a Canton-compatible wallet to hold and transact with CBTC. Options for institutional traders:

| **Wallet**                                                                                                                                                              | **Type**           | **Best For**                                       |
| ----------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------ | -------------------------------------------------- |
| **Zoro**                                                                                                                                                                | Self-custody       | Firms wanting SDK/API access and full control      |
| **Console**                                                                                                                                                             | Self-custody       | Browser-based with clear signing and risk checks   |
| **Loop**                                                                                                                                                                | Self-custody       | Web-based, no extensions needed, open source SDK   |
| **Cantor8**                                                                                                                                                             | Enterprise custody | Multi-signature security and regulatory compliance |
| For the full list of Canton wallets and SDK/API documentation, see the [Canton DeFi Ecosystem](https://docs.bitsafe.finance/trading-firms/canton-defi-ecosystem) guide. |                    |                                                    |

***

## Step 4: Acquire CBTC

> **Get CBTC into your wallet** Two paths depending on your infrastructure: **Option A: OTC Purchase** *(fastest, no Canton node required)*
>
> * Initiate a cross-chain CBTC swap with Trngle or an OTC purchase through Elk Capital
> * Ideal for firms without a Canton validator node
> * Contact Elk Capital for spread negotiation based on expected volume **Option B: Direct Minting** *(requires Canton validator node)*
> * Install the mint/burn software on your validator node
> * Call Rust APIs via cbtc-lib to mint CBTC directly from BTC
> * More cost-effective for high-volume operations
> * See the developer documentation at [docs.bitsafe.finance/product-suite/cbtc](https://docs.bitsafe.finance/product-suite/cbtc) for technical details

***

## Step 5: Choose and Connect to a Venue

> **Select your trading venue and integrate** See **Selecting a Trading Venue** for the full comparison. Quick summary:
>
> * **Elk / Trngle** (RFQ) - Institutional OTC, negotiable spreads, custom pairs
> * **Temple Digital** (CLOB) - Order book trading, 40% bonus reward share
> * **Tradefast** (AMM) - Uniswap V2 style, fastest integration
> * **Bron** - Intuitive interface, quick onboarding Each venue has its own API documentation and onboarding process. The BitSafe BD team will facilitate introductions.

***

## Step 6: Start Trading

> **You are live.**
>
> * Begin trading on your chosen venue
> * Every trade, swap, and lending transaction earns Canton Coin rewards
> * Rewards are transaction-count-based, not volume-based. High-frequency strategies earn more.
> * Review the **Prop Desk Playbook** for strategy recommendations **Recommended first trades:**
> * CBTC/USDXLR (primary pair, earns rewards from both assets)
> * CBTC/USDCx (familiar stable pairing)
> * CBTC/CC (Canton Coin exposure)

***

## Questions?

* **Email:** <sales@bitsafe.finance>
* **Common questions:** See the FAQ for Trading Firms
* **Technical questions:** See the developer documentation at [docs.bitsafe.finance/product-suite/cbtc](https://docs.bitsafe.finance/product-suite/cbtc)

***

> ℹ️ **Disclosures** Target yields are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Strategies carry risk; conduct independent due diligence. This is not investment advice.


# FAQ for Trading Firms

Common questions from trading firms evaluating or onboarding to CBTC on Canton. This FAQ is compiled from sales conversations, partner calls, and Slack discussions.

***

## Fees and Costs

### What are the fees for minting and burning CBTC?

Minting and burning fees are **currently waived.** This is subject to change in the future. Check with the BitSafe BD team for the latest fee schedule.

### Are there trading fees on the venues?

Each venue sets its own fee structure:

* **Elk / Trngle:** Negotiable spreads based on volume
* **Temple Digital:** No platform fees currently
* **Tradefast:** Standard AMM swap fees
* **Bron:** Check venue documentation

***

## Anti-Gaming and Compliance

### What counts as "legitimate" trading activity?

Strategies must involve **real economic risk.** This includes market making, arbitrage, inventory rebalancing, directional trading, lending, and liquidity provision. Each of these generates genuine market activity and is eligible for rewards.

### What activity is flagged or prohibited?

Canton's tokenomics accountability process flags and shuts down **scripted back-and-forth transfers** (A to B to A) designed solely to farm rewards. If your strategy does not involve swapping into another asset, managing inventory risk, or providing liquidity, it will likely be flagged.

## Wallets and Infrastructure

### What wallet do I need?

You need a **Canton-compatible wallet** that supports CBTC. Recommended options for institutional traders include Zoro (self-custody with SDK/API), Console (browser-based), Loop (web-based, open source SDK), and Cantor8 (enterprise custody with multi-sig). See the Canton DeFi Ecosystem guide for full details.

### Do I need to run a Canton validator node?

Not necessarily. You can acquire CBTC via **OTC purchase** through Elk Capital or Trngle without running a node. However, if you want to **mint CBTC directly** from BTC, you will need a validator node. Multi-tenant validator options are available for firms that want node access without the full infrastructure build.

### Can I use multiple wallets?

Yes. You can use multiple Canton-compatible wallets for trading CBTC across different venues.

***

## Venues and Trading

### Which venue should I choose?

It depends on your trading style:

* **Need institutional-size execution with custom pairs?** Elk / Trngle RFQ
* **Want an order book with the best reward economics?** Temple Digital CLOB (40% bonus)
* **Want fast deployment with familiar DeFi infra?** Tradefast AMM
* **Want the simplest starting point?** Bron
* **Prefer hands-off yield?** Temple Digital LP or SciFeCap SMA See **Selecting a Trading Venue** for the full comparison and decision guide.

### What trading pairs are available?

The primary pairs are:

* **CBTC / USDXLR** - Canton-native yield-bearing stablecoin (primary pair, earns rewards from both assets)
* **CBTC / USDCx** - Cross-chain stablecoin
* **CBTC / CC** - Canton Coin Availability varies by venue. Check the venue comparison table in **Selecting a Trading Venue**.

### Who are the current market participants?

Active institutional counterparties on Canton include Elk Capital Markets, SciFeCap, HashKey Cloud, Desyn, IMC, QCP, and others. The trading firm pipeline is growing rapidly.

***

## Onboarding

### How long does onboarding take?

Typically **1 to 2 weeks** from initial signup to first trade, depending on your firm's readiness, compliance review timeline, and chosen venue's integration requirements.

### What is the onboarding process?

1. Complete the CBTC signup form
2. Sign MSA and complete KYC/AML
3. Set up a Canton wallet
4. Acquire CBTC (OTC or direct mint)
5. Connect to your chosen venue
6. Start trading See the **Onboarding Checklist** for the full step-by-step guide.

***

## Security

### How is CBTC secured?

CBTC uses **FROST threshold signatures** over Bitcoin UTXOs for decentralized custody. There is no single custodian. The Attestor Network collectively approves mints and burns using a threshold signing scheme. CBTC is fully 1:1 backed by BTC at all times.

### Has CBTC been audited?

Yes. CBTC has been audited by **Quantstamp.** The full audit report is available at [certificate.quantstamp.com](https://certificate.quantstamp.com/).

***

## Getting Started

> 📝 **Ready to start?**
>
> * [Complete the CBTC Signup Form](https://bitsafe.typeform.com/to/NsiwLKIY)
> * Email: <sales@bitsafe.finance>
> * Read the **Onboarding Checklist** for the full step-by-step process

***

> ℹ️ **Disclosures** Target yields are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Strategies carry risk; conduct independent due diligence. This is not investment advice.


# CBTC Ecosystem Docs

Programmatically use products on Canton that support CBTC. Find documentation and links for venues, wallets, and other apps in the ecosystem.

> ℹ️ Each venue and wallet maintains its own documentation and onboarding process. For introductions or access requests, contact <sales@bitsafe.finance>.

***

## Trading Venues

| **Venue**          | **Type**     | **Docs / Website**                                        |   |
| ------------------ | ------------ | --------------------------------------------------------- | - |
| **Elk / Trngle**   | RFQ          | [trngle.xyz](https://trngle.xyz/)                         |   |
| **Temple Digital** | CLOB         | [templedigitalgroup.com](https://templedigitalgroup.com/) |   |
| **Tradefast**      | DEX / AMM    | [trade.fast](https://trade.fast/)                         |   |
| **Bron**           | Wallet + DEX | [bron.org](https://bron.org/)                             |   |
| **TradeCraft**     | AMM          | [tradecraft.fi](https://tradecraft.fi/)                   |   |
| **Cantex**         | DEX          | [cantex.io](https://cantex.io/)                           |   |
| **Kairo**          | DEX          | [kairo.ag](https://kairo.ag/)                             |   |

***

## Wallets

| **Wallet**    | **Type**           | **Docs / Website**                            |
| ------------- | ------------------ | --------------------------------------------- |
| **Zoro**      | Self-custody       | [zorowallet.com](https://zorowallet.com/)     |
| **Console**   | Self-custody       | [consolewallet.io](https://consolewallet.io/) |
| **Loop**      | Self-custody       | [cantonloop.com](https://cantonloop.com/)     |
| **Cantor8**   | Enterprise custody | [cantor8.tech](https://cantor8.tech/)         |
| **Bron**      | Self-custody       | [bron.org](https://bron.org/)                 |
| **Cansai**    | Self-custody       | [cansai.app](https://cansai.app/)             |
| **Cypherock** | Hardware           | [cypherock.com](https://cypherock.com/)       |

***

> ℹ️ **Disclosures** Venue APIs and SDKs are maintained by their respective providers. BitSafe does not guarantee the availability, accuracy, or stability of third-party documentation. Conduct your own technical due diligence. This is not investment advice.


# Resources

Consolidated links, documentation, and contact information for trading firms working with CBTC on Canton.

***

## Get Started

| **Resource**         | **Link**                                                                     |
| -------------------- | ---------------------------------------------------------------------------- |
| CBTC Signup Form     | [bitsafe.typeform.com/to/NsiwLKIY](https://bitsafe.typeform.com/to/NsiwLKIY) |
| Sales and BD Contact | <sales@bitsafe.finance>                                                      |

***

## Technical Documentation

| **Document**                            | **Link**                                                                                                                               |
| --------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------- |
| CBTC Developer Documentation            | [docs.bitsafe.finance/product-suite/cbtc](https://docs.bitsafe.finance/product-suite/cbtc)                                             |
| FROST Whitepaper (threshold signatures) | [eprint.iacr.org/2020/852](https://eprint.iacr.org/2020/852)                                                                           |
| Canton Network Whitepaper               | [canton.network/whitepapers](https://canton.network/whitepapers)                                                                       |
| Quantstamp Audit Report                 | [certificate.quantstamp.com](https://certificate.quantstamp.com/)                                                                      |
| CBTC Technical Documentation (legacy)   | [docs.bitsafe.finance/bitsafe-documentation/product-suite/cbtc](https://docs.bitsafe.finance/bitsafe-documentation/product-suite/cbtc) |
| FROST Security Deep Dive                | [docs.bitsafe.finance/.../a-deep-dive-into-frost](https://docs.bitsafe.finance/.../a-deep-dive-into-frost)                             |

***

## Venue Links

| **Venue**      | **Type**     | **Website**                               |
| -------------- | ------------ | ----------------------------------------- |
| Elk / Trngle   | RFQ          | [trngle.xyz](https://trngle.xyz/)         |
| Temple Digital | CLOB         | [temple.digital](https://temple.digital/) |
| Tradefast      | AMM          | [trade.fast](https://trade.fast/)         |
| Bron           | Wallet + DEX | [bron.org](https://bron.org/)             |
| TradeCraft     | AMM          | [tradecraft.fi](https://tradecraft.fi/)   |

***

## Wallet Links

| **Wallet** | **Website**                                   |
| ---------- | --------------------------------------------- |
| Zoro       | [zorowallet.com](https://zorowallet.com/)     |
| Console    | [consolewallet.io](https://consolewallet.io/) |
| Loop       | [cantonloop.com](https://cantonloop.com/)     |
| Cantor8    | [cantor8.tech](https://cantor8.tech/)         |
| Bron       | [bron.org](https://bron.org/)                 |
| Cansai     | [cansai.app](https://cansai.app/)             |
| Cypherock  | [cypherock.com](https://cypherock.com/)       |

***

## Trading Documentation

All institutional docs live at [docs.bitsafe.finance/trading-firms](https://docs.bitsafe.finance/trading-firms).

* **Why CBTC for Trading Firms:** Canton's differentiators, security model, and use cases
* **Prop Desk Playbook:** Strategies, reward mechanics, and anti-gaming rules
* **Selecting a Trading Venue:** Venue comparison, decision guide, and wallet options
* **Canton DeFi Ecosystem:** Full wallet, DEX, and DeFi app directory
* **Onboarding Checklist:** Step-by-step from signup to first trade
* **FAQ for Trading Firms:** Common questions answered Developer documentation lives at [docs.bitsafe.finance/product-suite/cbtc](https://docs.bitsafe.finance/product-suite/cbtc).

***

## Standardized Disclosures

> ℹ️ **Risk Disclosure** Target yields and reward projections are illustrative only and are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Trading strategies carry risk. Conduct independent due diligence before making any trading or allocation decisions. ℹ️ **Not Investment Advice** Nothing in this documentation constitutes investment, legal, or tax advice. All information is provided for informational purposes only.


# Glossary

Key terms and acronyms used across the institutional documentation. If you are coming from traditional finance or other blockchain networks, this page will help you navigate Canton-specific terminology.

***

## Assets and Tokens

**CBTC (Canton Bitcoin)**

Wrapped Bitcoin on the Canton Network. 1 CBTC is always backed 1:1 by BTC held in decentralized custody. CBTC is the primary asset for institutional trading on Canton.

**CC (Canton Coin)**

The native network rewards token on Canton. CC is earned through eligible transactions and distributed to participants. CC is not a stablecoin. Its value fluctuates based on market conditions.

**USDXLR**

A Canton-native yield-bearing stablecoin. The primary trading pair for CBTC. Trading CBTC/USDXLR earns rewards from both assets.

**USDCx**

A cross-chain stablecoin available on Canton. Provides a familiar stable pairing for BTC traders.

***

## Canton Network

**Canton Network**

An institutional-grade blockchain network designed for privacy, compliance, and atomic settlement. All participants are KYC-verified.

**Daml**

Canton's smart contract language. Used for building applications and defining transaction logic on the network.

**CIP-56**

Canton token standard. Defines how tokens (including CBTC) are created, transferred, and managed on Canton.

**Validator Node**

A node that participates in the Canton Network's consensus and transaction processing. Required for direct CBTC minting. Multi-tenant validator options are available for firms that do not want to run their own.

**Multi-Tenant Validator**

A shared validator node operated by a third-party provider. Allows firms to participate in the Canton Network without running their own infrastructure. Lower cost and faster setup than a dedicated node.

***

## Security and Custody

**FROST (Flexible Round-Optimized Schnorr Threshold)**

The threshold signature scheme used for CBTC's decentralized custody. FROST allows multiple parties to collectively sign Bitcoin transactions without any single party holding the full private key.

**Attestor Network**

The group of decentralized signers that collectively approve CBTC mints and burns using FROST threshold signatures. Currently operates on a 2-of-4 threshold.

**Threshold (M-of-N)**

The minimum number of attestors required to approve a transaction. For CBTC, 2 out of 4 attestors must sign to authorize a mint or burn.

**Proof of Reserve (PoR)**

Chainlink's verification mechanism confirming that all CBTC in circulation is fully backed 1:1 by BTC held in custody.

***

## Trading and Venues

**RFQ (Request for Quote)**

A trading model where a firm requests a price from a market maker and can accept or reject the quote. Used by Elk Capital / Trngle for institutional OTC execution.

**CLOB (Central Limit Order Book)**

A traditional exchange-style order book where buy and sell orders are matched by price and time priority. Used by Temple Digital.

**AMM (Automated Market Maker)**

A DeFi trading model where liquidity pools and mathematical formulas determine prices instead of an order book. Used by Tradefast.

**MEV (Miner/Maximal Extractable Value)**

The profit that can be extracted by reordering, inserting, or censoring transactions in a block. Canton eliminates MEV because it has no public mempool.

**Mempool**

A holding area for unconfirmed transactions visible to all network participants. Canton does not have a public mempool, which prevents front-running and sandwich attacks.

***

## Rewards and Economics

**Transaction-Count-Based Rewards**

Canton's reward model where every eligible transaction generates CC rewards regardless of transaction size. High-frequency strategies earn more rewards than low-frequency, high-volume strategies.

**Featured App (FA)**

A Canton application that has been designated as a Featured App, which affects reward multipliers for activity within that application.

**Anti-Gaming Policy**

Canton's tokenomics accountability process that detects and shuts down artificial transaction patterns (such as A to B to A transfers) designed to farm rewards without real economic activity.

***

## Agreements and Onboarding

**MSA (Master Service Agreement)**

The standard commercial agreement between a trading firm and BitSafe. Required before a firm can mint CBTC.

**KYC/AML (Know Your Customer / Anti-Money Laundering)**

Compliance checks required during onboarding. All Canton participants must be KYC-verified.

***

## Technical

**DAR (Daml Archive)**

A compiled Daml package file used to deploy smart contracts on Canton.

**cbtc-lib**

A Rust library for interacting with CBTC minting and burning functionality. Required for direct minting from BTC.

**Canton SDK**

The software development kit for building applications and submitting transactions on the Canton Network.


# Developers

Build integrations, wallets, and DeFi protocols with CBTC on the Canton Network. This section covers everything you need to go from first API call to production deployment.

## Getting Started

* [CBTC Overview](/developers/cbtc-overview) - Architecture and core concepts
* [SDK Setup and Installation](/developers/sdk-setup-and-installation) - Install cbtc-lib, upload the DAR files, and configure your environment. **Start here.**
* [CBTC Quick Start](/developers/cbtc-quick-start) - Mint your first CBTC in 15 minutes
* [CBTC Testnet Guide](/developers/cbtc-testnet-guide) - Test on Canton testnet before going live

## Core Operations

* [CBTC Minting and Burning](/developers/cbtc-minting-and-burning) - Convert BTC to CBTC and back with code
* [CBTC Authentication](/developers/cbtc-authentication) - Authenticate with the Canton Ledger API
* [CBTC API Reference](/developers/cbtc-api-reference) - Full API endpoint documentation
* [Instrument ID Management](/developers/instrument-id-management) - Manage CBTC instrument identifiers

## Advanced

* [Integration Guides](/developers/integration-guides) - Integrate CBTC into your platform
* [Technical Reference](/developers/technical-reference) - Detailed technical specifications
* [Security Deep Dive](/developers/security-deep-dive) - Threat model, FROST signatures, and audit results

## Reference

* [Resources](/developers/resources) - Audit reports, whitepapers, and external links
* [Changelog](/developers/changelog) - Release notes and version history


# CBTC Overview

> ⚠️ **API Disclaimer:** CBTC APIs are subject to change. There is no formal versioning policy today. Breaking changes are communicated via the site changelog.

***

## What is CBTC? Bitcoin on the Canton Network

CBTC is a **1:1 wrapped Bitcoin token** built on the [Canton Network](https://www.canton.network/), a privacy-first blockchain for institutional finance. Each CBTC is fully backed by native BTC held in decentralized custody using FROST threshold signatures. CBTC is **CIP-56 compliant**, meaning it works with any Canton token-standard-compatible tool out of the box.

CBTC brings Bitcoin's liquidity into Canton's privacy-enabled smart contract environment, where app developers and trading firms can build trading, DeFi, custody, and settlement applications without exposing positions to a public mempool. Unlike wrapped Bitcoin on public chains, CBTC transactions are private by default, eliminating MEV (Maximal Extractable Value) risks like front-running and sandwich attacks.

**Key properties:**

| Property          | Value                                                                                                                   |
| ----------------- | ----------------------------------------------------------------------------------------------------------------------- |
| **Backing**       | 1 CBTC = 1 BTC, always                                                                                                  |
| **Standard**      | CIP-56 (Canton Instrument Protocol)                                                                                     |
| **Custody**       | Decentralized via FROST threshold signatures (no single party can move reserves)                                        |
| **Network**       | Canton Network (permissioned, private transactions)                                                                     |
| **Audit**         | [Quantstamp audit report](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html) |
| **Confirmations** | 6 Bitcoin block confirmations (\~60 minutes) for minting                                                                |

***

## CBTC Architecture: How Wrapped Bitcoin Works on Canton

The CBTC system bridges Bitcoin's UTXO model to Canton's Daml-based smart contract network through three layers:

### 1. Bitcoin Layer

Bitcoin transactions are monitored and verified. A user sends BTC to a generated Taproot deposit address. The system waits for 6 block confirmations before proceeding.

### 2. Attestor Network

A decentralised network of institutional-grade node operators independently verify Bitcoin deposits and withdrawals. Each Attestor runs nodes on **both** the Bitcoin and Canton networks. Key details:

* **Operators:** Pre-screened institutional node operators (including providers like Finoa and Nethermind)
* **Threshold:** A configurable M-of-N threshold of Attestors must approve every mint and burn operation
* **Coordination:** A Coordinator executes periodic checks (every 60-120 seconds), monitors deposit accounts, constructs Bitcoin transactions, and submits governance actions
* **No unilateral control:** No single party - including BitSafe or the Coordinator - can mint, burn, or move BTC without threshold approval

### 3. Canton Asset Layer

Daml contracts mint and burn CBTC tokens, but **only** after the required threshold of Attestor signatures is reached on the governance contract. CBTC is then held in the user's Canton party, fully under their control.

```mermaid
flowchart LR
 A["Bitcoin Network<br>(Taproot deposit address)"] -->|"6 confirmations"| B["Attestor Network<br>(FROST threshold signing)"]
 B -->|"M-of-N approval"| C["Canton Network<br>(Daml contracts mint CBTC)"]
 C -->|"Burn request"| B
 B -->|"Signed BTC tx"| A
```

***

## Security Model: FROST Threshold Signatures for Bitcoin Custody

CBTC's security rests on **FROST** (Flexible Round-Optimised Schnorr Threshold Signatures), a cryptographic protocol added to Bitcoin with the Taproot upgrade.

**Why FROST matters for developers:**

* **Taproot-native:** Deposit addresses are standard P2TR addresses. Any wallet that supports Taproot can send BTC to mint CBTC.
* **Indistinguishable on-chain:** FROST signatures look identical to regular single-signature Bitcoin transactions. No one can tell from the blockchain that a threshold scheme is in use.
* **Smaller transactions, lower fees:** Compared to traditional on-chain multisig, FROST produces a single aggregated signature regardless of how many Attestors participated.
* **No single point of failure:** Even if some Attestors go offline, the system continues to operate as long as the threshold is met. For a full technical deep dive, see the [Security Deep Dive](https://docs.bitsafe.finance/developers/security-deep-dive) page. For the original research, see the [FROST whitepaper](https://eprint.iacr.org/2020/852).

***

## What You Can Build with Wrapped Bitcoin on Canton

CBTC is a foundational layer for building institutional-grade financial products on Canton:

* **DeFi Protocols** - DEXs, lending platforms, and liquidity pools using CBTC as collateral
* **Custody and Wallet Solutions** - Institutional-grade wallets supporting CBTC and Canton-native assets
* **Structured Products** - Yield-generating vaults, options strategies, and derivatives
* **Payment and Settlement** - Instant, low-cost cross-border transactions
* **Trading Systems** - Spot and perpetual trading with Canton's privacy (no public mempool, no MEV)

***

## Developer Resources

| Resource              | Description                                           | Link                                                                                                                               |
| --------------------- | ----------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------- |
| **cbtc-lib (Rust)**   | SDK for minting, burning, sending, and receiving CBTC | [GitHub](https://github.com/DLC-link/cbtc-lib) · [Setup guide](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) |
| **canton-lib**        | Lower-level Canton interaction library                | [GitHub](https://github.com/DLC-link/canton-lib/)                                                                                  |
| **CBTC DAR files**    | Daml packages to install on your Canton participant   | [GitHub](https://github.com/DLC-link/cbtc-lib/tree/main/cbtc-dars)                                                                 |
| **FROST Whitepaper**  | Original threshold signature research                 | [ePrint](https://eprint.iacr.org/2020/852)                                                                                         |
| **Canton Whitepaper** | Canton Network technical overview                     | [canton.network](https://canton.network/)                                                                                          |
| **Quantstamp Audit**  | Security audit of CBTC smart contracts                | [View Report](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html)                        |
| **Data API**          | Analytics and rewards API for institutional clients   | [API Reference](https://docs.bitsafe.finance/developers/cbtc-api-reference)                                                        |

***

## Next Steps

* **Ready to code?** Start with [SDK Setup and Installation](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) to install `cbtc-lib` and configure your environment, then follow the [Developer Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start) to mint your first CBTC in 15 minutes
* **Need API details?** See the [API Reference](https://docs.bitsafe.finance/developers/cbtc-api-reference) for Canton Ledger API endpoints
* **Setting up authentication?** See the [Authentication Guide](https://docs.bitsafe.finance/developers/cbtc-authentication) for Keycloak setup (and an Auth0 community example)
* **Want to test first?** See the [Testnet Guide](https://docs.bitsafe.finance/developers/cbtc-testnet-guide) for sandbox environment setup

***


# SDK Setup and Installation

> ⚠️ **API Disclaimer.** CBTC APIs have no formal versioning policy today. All SDK interfaces described in this guide are **subject to change**. Breaking changes are communicated via the changelog.

***

This page is your single reference for installing and configuring everything you need to build with CBTC. If you've already completed setup, head straight to the [Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start) to mint your first wrapped Bitcoin.

***

## System Requirements

| Requirement                 | Details                                                                                                                                                                              |
| --------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| **Rust toolchain**          | Latest stable. Install via [rustup.rs](https://rustup.rs/)                                                                                                                           |
| **Canton participant node** | Running and connected to devnet, testnet, or mainnet. See [Canton documentation](https://docs.digitalasset.com/canton)                                                               |
| **DA Registry Utility**     | Installed and configured. See [Digital Asset Utilities docs](https://docs.digitalasset.com/utilities/mainnet/index.html)                                                             |
| **Keycloak credentials**    | Host, realm, client ID, username, and password for your environment                                                                                                                  |
| **Party ID**                | Your Canton Party ID, obtained during onboarding                                                                                                                                     |
| **Minter credential**       | Only required to **mint or burn** CBTC. Issued to your party by the CBTC registrar; request one via <sales@bitsafe.finance>. Holding, sending, and receiving CBTC do not require it. |

***

## Install cbtc-lib (Rust)

`cbtc-lib` is BitSafe's primary SDK for CBTC operations: minting, burning, transferring, UTXO management, and balance queries. It wraps the Canton Ledger API with type-safe Rust functions.

* **Repository:** [github.com/DLC-link/cbtc-lib](https://github.com/DLC-link/cbtc-lib)
* **Current version:** v0.6.4
* **Licence:** *Check repository*

### Add to your project

Add `cbtc-lib` to your `Cargo.toml`:

```toml
[dependencies]
cbtc = { git = "ssh://git@github.com/DLC-link/cbtc-lib.git", tag = "v0.6.4" }
```

> 📌 **Pin your version.** Always reference a specific tag (e.g. `v0.6.4`) rather than `main`. The library is under active development and `main` may contain breaking changes between releases.

### Key modules

| Module                      | Purpose                                                          |
| --------------------------- | ---------------------------------------------------------------- |
| `cbtc::mint_redeem::mint`   | Create deposit accounts, get Bitcoin deposit addresses           |
| `cbtc::mint_redeem::redeem` | Create withdraw accounts, burn CBTC and withdraw to BTC          |
| `cbtc::transfer`            | Send CBTC to another party (creates transfer offer)              |
| `cbtc::accept`              | Accept incoming CBTC transfer offers                             |
| `cbtc::active_contracts`    | Query current CBTC holdings for a party                          |
| `cbtc::consolidate`         | Merge multiple UTXO holdings into fewer contracts                |
| `cbtc::split`               | Split a single holding into multiple UTXOs                       |
| `cbtc::batch`               | Batch operations for sending to multiple recipients              |
| `cbtc::distribute`          | Distribute CBTC across multiple parties                          |
| `cbtc::cancel_offers`       | Cancel pending outgoing transfer offers                          |
| `cbtc::credentials`         | List and accept Minter credentials (required to mint or burn)    |
| `cbtc::allocation`          | Allocate CBTC into DvP settlement legs (delivery-versus-payment) |

***

## Install canton-lib

`canton-lib` is now a **Rust workspace** containing multiple crates that `cbtc` depends on. It handles Canton Ledger API communication, authentication, and Daml contract interactions.

* **Repository:** [github.com/DLC-link/canton-lib](https://github.com/DLC-link/canton-lib)
* **Crates:** `keycloak`, `ledger`, `registry`, `common` (all at v0.6.1)

### Add to your project

Add the canton-lib crates you need to your `Cargo.toml`:

```toml
[dependencies]
keycloak = { git = "ssh://git@github.com/DLC-link/canton-lib.git", tag = "v0.6.1" }
ledger = { git = "ssh://git@github.com/DLC-link/canton-lib.git", tag = "v0.6.1" }
registry = { git = "ssh://git@github.com/DLC-link/canton-lib.git", tag = "v0.6.1" }
common = { git = "ssh://git@github.com/DLC-link/canton-lib.git", tag = "v0.6.1" }
```

> 📌 **Match the tag `cbtc-lib` depends on.** `cbtc-lib` v0.6.4 pins canton-lib v0.6.1. If you add these crates at a different tag than the one `cbtc-lib` uses, Cargo will resolve two incompatible copies of the same types and your build will fail with confusing mismatched-type errors.

The `keycloak` crate provides authentication helpers used across all CBTC operations.

**Password-grant authentication** (for user-facing flows):

```rust
use keycloak::login::{password, password_url, PasswordParams};

let auth = password(PasswordParams {
 client_id: keycloak_client_id.clone(),
 username: keycloak_username.clone(),
 password: keycloak_password.clone(),
 url: password_url(&keycloak_host, &keycloak_realm),
}).await?;

let access_token = auth.access_token;
```

**Client credentials authentication** (for service-to-service / backend flows):

```rust
use keycloak::login::{client_credentials, client_credentials_url, ClientCredentialsParams};

let auth = client_credentials(ClientCredentialsParams {
 url: client_credentials_url("https://your-keycloak-host", "your-realm"),
 client_id: "your-client-id".to_string(),
 client_secret: "your-client-secret".to_string(),
}).await?;

let access_token = auth.access_token;
```

***

## Install CBTC DAR Files

DAR (Daml Archive) files contain the smart contract templates that power CBTC on Canton. They must be installed on your participant node before you can interact with CBTC.

**Download:** [github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars](https://github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars)

The latest CBTC DAR is **`cbtc-1.2.1`**, shipped in `cbtc-lib` v0.6.4. DAR versions and crate versions are numbered independently.

Install the DAR files on your Canton participant node using the Canton console or your deployment tooling. The specific installation method depends on your Canton setup. Refer to the [Canton documentation](https://docs.digitalasset.com/canton) for details.

> 💡 **Install every DAR version, not just the newest.** The repository ships all released DARs (`cbtc-1.0.0` through `cbtc-1.2.1`). Older versions are required to interact with contracts still live on the network from earlier releases. You can verify what your participant is missing with the `cbtc::dar_check` module.

> 💡 **DAR version and Instrument IDs are linked.** When DAR files are upgraded on the network, Instrument IDs may change. Always fetch Instrument IDs dynamically from the metadata endpoint rather than hardcoding them. See the [Instrument ID Management](https://docs.bitsafe.finance/developers/instrument-id-management) page for the polling pattern.

***

## Environment Configuration

Set these variables before running any CBTC commands or code. Values differ per environment.

| Variable                 | Devnet                                                                                      | Testnet                                                                                             | Mainnet                                                                             |
| ------------------------ | ------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------- |
| `REGISTRY_URL`           | [`https://api.utilities.digitalasset-dev.com`](https://api.utilities.digitalasset-dev.com/) | [`https://api.utilities.digitalasset-staging.com`](https://api.utilities.digitalasset-staging.com/) | [`https://api.utilities.digitalasset.com`](https://api.utilities.digitalasset.com/) |
| `BITSAFE_API_URL`        | [`https://api.devnet.bitsafe.finance`](https://api.devnet.bitsafe.finance)                  | [`https://api.testnet.bitsafe.finance`](https://api.testnet.bitsafe.finance)                        | [`https://api.mainnet.bitsafe.finance`](https://api.mainnet.bitsafe.finance)        |
| `DECENTRALIZED_PARTY_ID` | *Provided during onboarding*                                                                | *Provided during onboarding*                                                                        | *Provided during onboarding*                                                        |

> 💡 **`BITSAFE_API_URL`** is the BitSafe API gateway, which serves the `/cbtc/v1/*` endpoints behind deposit accounts, deposit addresses, and withdrawals. `cbtc-lib` reads it and passes it as the `api_url` parameter to `get_account_contract_rules`, `get_bitcoin_address`, and `submit_withdraw`. An Attestor or Coordinator host will not work in its place.

### Example.env file

```bash
# Environment (choose one: devnet, testnet, mainnet)
REGISTRY_URL="https://api.utilities.digitalasset-staging.com"
BITSAFE_API_URL="https://api.testnet.bitsafe.finance"
CANTON_NETWORK="canton-testnet"
PARTY_ID="your-party-id"

# Authentication (Keycloak)
KEYCLOAK_HOST="https://your-keycloak-host"
KEYCLOAK_REALM="your-realm"
KEYCLOAK_CLIENT_ID="your-client-id"
KEYCLOAK_USERNAME="your-username"
KEYCLOAK_PASSWORD="your-password"

# Canton participant
LEDGER_HOST="https://your-ledger-host"
```

***

## Verify Your Installation

Run this minimal check to confirm everything is wired up:

```rust
use keycloak::login::{password, password_url, PasswordParams};
use cbtc::active_contracts;

#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
 // 1. Authenticate
 let auth = password(PasswordParams {
 client_id: std::env::var("KEYCLOAK_CLIENT_ID")?,
 username: std::env::var("KEYCLOAK_USERNAME")?,
 password: std::env::var("KEYCLOAK_PASSWORD")?,
 url: password_url(
 &std::env::var("KEYCLOAK_HOST")?,
 &std::env::var("KEYCLOAK_REALM")?,
 ),
 }).await?;

 println!("✅ Authenticated successfully");

 // 2. Query holdings (should return empty if no CBTC yet)
 let holdings = active_contracts::get(active_contracts::Params {
 ledger_host: std::env::var("LEDGER_HOST")?,
 party: std::env::var("PARTY_ID")?,
 access_token: auth.access_token,
 }).await?;

 println!("✅ Connected to Canton. Current CBTC holdings: {}", holdings.len());
 Ok(())
}
```

If both checks pass, you're ready. Head to the [Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start) to mint your first CBTC.

***

## Next Steps

* [**Quick Start**](https://docs.bitsafe.finance/developers/cbtc-quick-start) - Mint your first wrapped Bitcoin in 15 minutes
* [**CBTC Minting and Burning**](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) - The mint and burn lifecycle in depth, with error handling and recovery patterns
* [**API Reference**](https://docs.bitsafe.finance/developers/cbtc-api-reference) - Full Canton Ledger API endpoint documentation
* [**Instrument ID Management**](https://docs.bitsafe.finance/developers/instrument-id-management) - How to fetch and poll for the latest CBTC Instrument IDs
* [**Authentication Guide**](https://docs.bitsafe.finance/developers/cbtc-authentication) - Detailed Keycloak setup and Auth0 community example
* [**Testnet Guide**](https://docs.bitsafe.finance/developers/cbtc-testnet-guide) - Get testnet CBTC from the faucet and test before going live

***


# CBTC Quick Start

> ⚠️ **API Disclaimer.** CBTC APIs have no formal versioning policy today. All endpoints and library interfaces described in this guide are **subject to change**. Breaking changes are communicated via the changelog. This disclaimer will be updated once a formal versioning and stability policy is established.

This step-by-step guide walks you through minting your first CBTC (wrapped Bitcoin) on the Canton Network. You will authenticate with Keycloak, create a deposit account, send BTC to a Taproot address, and receive 1:1 backed CBTC on your Canton participant node. The full process takes about 15 minutes of active work plus \~60 minutes of Bitcoin confirmation time.

> 🎯 **What you will accomplish**
>
> * Authenticate to the Canton Network via Keycloak
> * Create a CBTC deposit account
> * Obtain a Bitcoin deposit address
> * Send BTC and wait for confirmation
> * Verify your CBTC balance
> * Send CBTC to another party (two-phase transfer)

> 🛠️ **Install the SDK first.** Every code example on this page uses the `cbtc-lib` Rust SDK. If you have not installed it yet, start with [SDK Setup and Installation](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) — it covers installing `cbtc-lib` and `canton-lib`, uploading the CBTC DAR files to your participant node, and configuring your environment variables. Come back here once the verification check on that page passes.

***

## Prerequisites for Minting CBTC

Before you begin minting wrapped Bitcoin on Canton, make sure you have the following:

| Requirement                 | Description                                                                                                                                                                                                                                                          |
| --------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| **Canton participant node** | A running Canton participant node connected to the network. See [Canton documentation](https://docs.digitalasset.com/canton) for setup.                                                                                                                              |
| **DA Registry Utility**     | Installed and configured. See [Digital Asset Utilities docs](https://docs.digitalasset.com/utilities/mainnet/index.html).                                                                                                                                            |
| **Keycloak credentials**    | A valid Keycloak host, realm, client ID, username, and password for your environment.                                                                                                                                                                                |
| **Party ID**                | Your Canton Party ID, obtained during onboarding.                                                                                                                                                                                                                    |
| **Minter credential**       | **Required to mint or burn.** Issued to your party by the CBTC registrar as part of onboarding. Request one via <sales@bitsafe.finance>. See [Minting and Burning](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) for how to check and accept it. |
| **Rust toolchain**          | If using cbtc-lib (Rust). Install via [rustup.rs](https://rustup.rs/).                                                                                                                                                                                               |
| **BTC to deposit**          | Real BTC (mainnet) or testnet BTC (testnet). For testnet, you can use the [CBTC Testnet Faucet](https://cbtc-faucet.bitsafe.finance/) to get test CBTC directly. For mainnet, you mint CBTC by depositing real BTC.                                                  |

***

## Choose Your CBTC Environment: Testnet or Mainnet

CBTC is available on three environments. **Start with testnet** for experimentation, then move to mainnet for production. CBTC also exists on Devnet, but minting and withdrawals are not available to external users on Devnet. You can use the faucet to obtain test CBTC for development.

> 🧪 **Testnet vs. Mainnet: what is identical and what differs**
>
> * **Identical:** DAR file, API surface, mint/burn flows, governance model, two-phase transfer mechanics
> * **Differs:** Attestor set (smaller on testnet), confirmation times (may be faster), Instrument IDs (different from mainnet), faucet-only BTC on testnet (no real value)
> * **Mocked or unavailable on testnet:** Real BTC settlement, production Attestor SLAs, mainnet fee structure
> * **Operational note:** Testnet may be reset without notice. Testnet CBTC balances and transaction history may not persist across resets. Do not rely on testnet state for production planning.

### Environment Configuration

| Variable                 | Devnet                                                                                      | Testnet                                                                                             | Mainnet                                                                              |
| ------------------------ | ------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------ |
| `REGISTRY_URL`           | [`https://api.utilities.digitalasset-dev.com`](https://api.utilities.digitalasset-dev.com/) | [`https://api.utilities.digitalasset-staging.com`](https://api.utilities.digitalasset-staging.com/) | [`https://api.utilities.digitalasset.com`](https://api.utilities.digitalasset.com/)  |
| `BITSAFE_API_URL`        | [`https://api.devnet.bitsafe.finance`](https://api.devnet.bitsafe.finance)                  | [`https://api.testnet.bitsafe.finance`](https://api.testnet.bitsafe.finance)                        | [`https://api.mainnet.bitsafe.finance`](https://api.mainnet.bitsafe.finance)         |
| `DECENTRALIZED_PARTY_ID` | `cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff`        | `cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f`                | `cbtc-network::12205af3b949a04776fc48cdcc05a060f6bda2e470632935f375d1049a8546a3b262` |

Set these as environment variables before running any commands:

```bash
export BITSAFE_API_URL="https://api.testnet.bitsafe.finance"
export REGISTRY_URL="<your-registry-url>"
export CANTON_NETWORK="canton-testnet"
export DECENTRALIZED_PARTY_ID="<your-decentralized-party-id>"
export KEYCLOAK_HOST="https://your-keycloak-host"
export KEYCLOAK_REALM="your-realm"
export KEYCLOAK_CLIENT_ID="your-client-id"
export KEYCLOAK_USERNAME="your-username"
export KEYCLOAK_PASSWORD="your-password"
export LEDGER_HOST="https://your-ledger-host"
export PARTY_ID="your-party-id"
```

***

## Step 1: Authenticate with Keycloak

All CBTC operations require a valid Keycloak access token. The `canton-lib` crate provides a helper for this.

### Using cbtc-lib (Rust)

```rust
use keycloak::login::{password, password_url, PasswordParams};

let auth = password(PasswordParams {
 client_id: keycloak_client_id.clone(),
 username: keycloak_username.clone(),
 password: keycloak_password.clone(),
 url: password_url(&keycloak_host, &keycloak_realm),
}).await?;

let access_token = auth.access_token;
```

### Using the Keycloak API directly

```bash
curl -X POST "${KEYCLOAK_HOST}/auth/realms/${KEYCLOAK_REALM}/protocol/openid-connect/token" \
 -H "Content-Type: application/x-www-form-urlencoded" \
 -d "grant_type=password" \
 -d "client_id=${KEYCLOAK_CLIENT_ID}" \
 -d "username=${KEYCLOAK_USERNAME}" \
 -d "password=${KEYCLOAK_PASSWORD}"
```

Save the `access_token` from the response. You will pass it as a Bearer token in all subsequent API calls.

> 💡 **`api_url` in the code examples below** is the BitSafe API base URL — the value you set as `BITSAFE_API_URL` above. It serves the `/cbtc/v1/*` endpoints that back deposit accounts, deposit addresses, and withdrawals.

***

## Step 2: Create a Deposit Account

A deposit account maps your Canton Party ID to a unique Bitcoin deposit address. You only need to create this once; the address can be reused for future deposits.

> ⚠️ **This step requires a Minter credential.** Deposit account creation fails without one. If you have not been issued a Minter credential yet, request one via <sales@bitsafe.finance>. See [Minting and Burning](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) for how to check for and accept your credential.

### Using cbtc-lib

```rust
use cbtc::mint_redeem::{mint, attestor};

// First get account rules from the Attestor
let account_rules = attestor::get_account_contract_rules(&api_url).await?;

let deposit_account = mint::create_deposit_account(mint::CreateDepositAccountParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 account_rules,
 credential_cids: minter_credential_cids.clone(),
}).await?;
```

### Using the Canton API directly

Submit a `CreateDepositAccount` command to the Canton Ledger API v2 endpoint. You can fetch the `CBTCDepositAccountRules` contract from an Attestor's `GET /cbtc/v1/account-contract-rules` endpoint.

```bash
curl -X POST '${LEDGER_HOST}/v2/commands/submit-and-wait-for-transaction-tree' \
 --header 'Authorization: Bearer ${ACCESS_TOKEN}' \
 --data '{
 "commands": [
 {
 "ExerciseCommand": {
 "templateId": "#cbtc:CBTC.DepositAccount:CBTCDepositAccountRules",
 "contractId": "${DA_RULES_CID}",
 "choice": "CBTCDepositAccountRules_CreateDepositAccount",
 "choiceArgument": {
 "owner": "${OWNER_PARTY}"
 }
 }
 }
 ],
 "actAs": [
 "${OWNER_PARTY}"
 ],
 "commandId": "someCommandID",
 "disclosedContracts": [
 {
 "templateId": "#cbtc:CBTC.DepositAccount:CBTCDepositAccountRules",
 "contractId": "${DA_RULES_CID}",
 "createdEventBlob": "${DA_RULES_BLOB}",
 "synchronizerId": ""
 }
 ]
}'
```

{% hint style="info" %}
Note: The submit-and-wait-for-transaction-tree endpoint is deprecated in Canton 3.5 but remains functional. Consider migrating to submit-and-wait-for-transaction for new integrations.
{% endhint %}

> ℹ️ **Ephemeral contract IDs.** `DA_RULES_CID` and `DA_RULES_BLOB` are ephemeral contract IDs. Query them from the Active Contract Service (`POST /v2/state/active-contracts`) at submit time. These IDs change after every consuming exercise.

***

## Step 3: Get Your Bitcoin Deposit Address

Once the deposit account is created, retrieve the Bitcoin address associated with it. This address is derived from the Deposit Account's `id` field (or the `contract_id` if the Deposit Account is new).

### Using cbtc-lib

```rust
let btc_address = mint::get_bitcoin_address(mint::GetBitcoinAddressParams {
 api_url: api_url.clone(),
 account_id: deposit_account.contract_id.clone(),
}).await?;

println!("Send BTC to: {}", btc_address);
```

### Using the BitSafe API directly

Retrieve the deposit address from:

```
GET ${BITSAFE_API_URL}/cbtc/v1/bitcoin-address/{accountId}
```

Use the deposit account's `id` field as `accountId`.

**Important:** This address can be reused indefinitely for future deposits. You can also request additional deposit addresses if needed.

***

## Step 4: Send BTC

Send Bitcoin to the deposit address using any standard Bitcoin wallet or tooling.

> ⚠️ **Deposits are subject to per-account limits.** By default the minimum is **0.0001 BTC** and the maximum is **5 BTC**. A deposit outside that range will not be minted. Limits are set per account and can be adjusted on request - see [Transaction Limits](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) for how to read your account's actual limits at runtime rather than assuming the defaults.

```javascript
Bitcoin address: [your deposit address from Step 3]
```

After sending, you need to wait for **6 Bitcoin block confirmations** before the Attestor network will process the deposit.

***

## Step 5: Wait for Confirmations and Auto-Minting

Once your BTC transaction reaches 6 confirmations:

1. The **Attestor network** detects the confirmed deposit
2. Each Attestor independently verifies the transaction
3. When a threshold of Attestors confirm (via `ConfirmDepositAction` on the CBTC Governance module), CBTC is **automatically minted** to your Canton Party
4. No further action is required from you This process typically takes 60 to 90 minutes, depending on Bitcoin block times.

***

## Step 6: Check Your CBTC Balance

### Using cbtc-lib

```rust
use cbtc::active_contracts;

let holdings = active_contracts::get(active_contracts::Params {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
}).await?;

println!("CBTC holdings: {} contract(s)", holdings.len());
```

### Using the Canton API directly

Query active contracts filtered by the token holding interface:

```bash
curl -X POST "${LEDGER_HOST}/v2/state/active-contracts" \
 -H "Authorization: Bearer ${ACCESS_TOKEN}" \
 -H "Content-Type: application/json" \
 -d '{
 "filter": {
 "interfaceFilters": [{
 "interfaceId": "#splice-api-token-holding-v1:Splice.Api.Token.HoldingV1:Holding"
 }]
 },
 "activeAtOffset": "${LATEST_OFFSET}"
 }'
```

> 💡 **Filtering required.** This query returns all token holdings, including Canton Coin (CC). To isolate your CBTC balance, you must filter the results client-side by the CBTC `instrumentId`. The `cbtc-lib` library handles this automatically via `active_contracts::get`. There is no single curl that can query and filter for CBTC holdings in one step. The `activeAtOffset` must be set to the actual latest offset from your ledger.

> 💡 **UTXO model.** CBTC uses a UTXO model similar to Bitcoin. Your balance may be spread across multiple holding contracts (soft limit of 10 UTXOs per party per token type). Use the `cbtc::consolidate` module to merge UTXOs, or `cbtc::split` to divide them.

***

## Step 7: Transfer CBTC Between Canton Parties

CBTC transfers use a **two-phase model**: the sender creates an offer, and the receiver accepts it. This ensures both parties explicitly consent to the transfer.

### Phase 1: Create a transfer offer (sender)

```rust
use cbtc::transfer;

transfer::submit(transfer::Params {
 transfer: common::transfer::Transfer {
 sender: sender_party_id.clone(),
 receiver: receiver_party_id.clone(),
 amount: cbtc::DamlDecimal::parse("0.01")?,
 instrument_id: common::transfer::InstrumentId {
 admin: decentralized_party_id.clone(),
 id: "CBTC".to_string(),
 },
 requested_at: chrono::Utc::now().to_rfc3339(),
 execute_before: (chrono::Utc::now() + chrono::Duration::hours(168)).to_rfc3339(),
 input_holding_cids: None,
 meta: None,
 },
 ledger_host: ledger_host.clone(),
 access_token: access_token.clone(),
 registry_url: registry_url.clone(),
 decentralized_party_id: decentralized_party_id.clone(),
}).await?;
```

### Phase 2: Accept the transfer (receiver)

```rust
use cbtc::accept;

accept::submit(accept::Params {
 transfer_offer_contract_id: transfer_contract_id.clone(),
 receiver_party: receiver_party_id.clone(),
 ledger_host: ledger_host.clone(),
 access_token: receiver_access_token.clone(),
 registry_url: registry_url.clone(),
 decentralized_party_id: decentralized_party_id.clone(),
}).await?;
```

> ℹ️ **No curl example for transfers.** The raw API transfer flow requires 5-6 sequential API calls with contract disclosures and is too complex to represent as a single curl example. Use `cbtc-lib` for transfers, or refer to the [Canton Utility docs](https://docs.digitalasset.com/utilities/mainnet/index.html) for the full API sequence.

> 💡 **This is a free-of-payment (FOP) transfer.** CBTC moves in one direction with nothing exchanged in return. If you need **delivery-versus-payment** — where CBTC only moves if a second leg moves atomically with it — use the `cbtc::allocation` module instead. See [DvP Settlement Using Allocations](https://docs.bitsafe.finance/developers/integration-guides) in the Integration Guides.

***

## Redeem CBTC: Convert Wrapped Bitcoin Back to BTC

To convert CBTC back to BTC (this also requires a Minter credential):

1. **Create a withdraw account** specifying your Bitcoin destination address using the `cbtc::mint_redeem::redeem` module
2. **Submit the withdrawal** which burns CBTC on Canton
3. The **Attestor network** detects the burn and constructs a Bitcoin transaction
4. Attestors sign the transaction via threshold signing (FROST)
5. The BTC transaction is broadcast to the Bitcoin network

### Using cbtc-lib

```rust
use cbtc::mint_redeem::redeem;

// 1. Create a withdraw account with your BTC destination address
let withdraw_account = redeem::create_withdraw_account(redeem::CreateWithdrawAccountParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 account_rules_contract_id: rules.wa_rules.contract_id.clone(),
 account_rules_template_id: rules.wa_rules.template_id.clone(),
 account_rules_created_event_blob: rules.wa_rules.created_event_blob.clone(),
 destination_btc_address: btc_destination_address.clone(),
 credential_cids: minter_credential_cids.clone(),
}).await?;

// 2. Submit the withdrawal (burns CBTC, Attestors process BTC payout)
let updated_account = redeem::submit_withdraw(redeem::SubmitWithdrawParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 api_url: api_url.clone(),
 withdraw_account_contract_id: withdraw_account.contract_id.clone(),
 amount: cbtc::DamlDecimal::parse("0.001")?,
 holding_contract_ids: holding_ids,
 credential_cids: Some(minter_credential_cids.clone()),
}).await?;

println!("Pending balance: {}", updated_account.pending_balance);
```

### Using the Canton API directly

Submit a `CBTCWithdrawAccount_Withdraw` command. You can get the correct `extraArgs` and contract disclosures from an Attestor's `GET /cbtc/v1/token-standard-contracts` endpoint. The `contractIds`, `templateIds`, and `blobs` in this example are for illustration only:

```bash
curl -X POST '${LEDGER_HOST}/v2/commands/submit-and-wait-for-transaction-tree' \
 --header 'Authorization: Bearer ${ACCESS_TOKEN}' \
 --data '{
 "commands": [
 {
 "ExerciseCommand": {
 "templateId": "#cbtc:CBTC.WithdrawAccount:CBTCWithdrawAccount",
 "contractId": "${WA_CID}",
 "choice": "CBTCWithdrawAccount_Withdraw",
 "choiceArgument": {
 "amount": "${AMOUNT}",
 "tokens": [
 "${INPUT_HOLDING}"
 ],
 "burnMintFactoryCid": "${ALLOCATION_FACTORY_CID}",
 "extraArgs": {
 "context": {
 "values": {
 "utility.digitalasset.com/instrument-configuration": {
 "tag": "AV_ContractId",
 "value": "00da61fcfa2d9b358c606f040a1d635fbabe4265d33908744a148a80be0dcdc383ca111220e86787467ef7be665f68b813a30de6b0480955dcb514ef29832720618375dee5"
 },
 "utility.digitalasset.com/app-reward-configuration": {
 "tag": "AV_ContractId",
 "value": "00bee23612f3c82dd6091e64ffde81cb535e7b446d7ebdf6d91329502c6023d1cdca1112209569dade5e20bf97f963882f6387293034a82f716d2b0df28820a82048f5f86c"
 },
 "utility.digitalasset.com/featured-app-right": {
 "tag": "AV_ContractId",
 "value": "001c6e92181f8de9e4d15956e33f90db3085c518747de627134b6850459bf3662fca111220ee87bf1e3b05ed4d3f8a6c336290660f23409cb8d11a028e1073137eac8f78bf"
 },
 "utility.digitalasset.com/issuer-credentials": {
 "tag": "AV_List",
 "value": [
 {
 "tag": "AV_ContractId",
 "value": "0058feffeeaa48cc5526c723c4877af4f6abe3c76131c54ba0d63c6da299f8681bca111220b7032514b6b448d75ea6d9eefe01f0a345504e897a5f2e72fabf974322b20b07"
 }
 ]
 }
 }
 },
 "meta": {
 "values": {
 "splice.lfdecentralizedtrust.org/reason": "CBTC Burn"
 }
 }
 }
 }
 }
 }
 ],
 "actAs": [
 "${OWNER_PARTY}"
 ],
 "commandId": "someCommandId",
 "disclosedContracts": [
 {
 "templateId": "82798df018301852704f210b97adaabf76d3ecd37d889e1bf96b5f31a20eea34:Utility.Registry.App.V0.Service.AllocationFactory:AllocationFactory",
 "contractId": "00d58a5f061f086b3c4b405b57ca08f4cefcb7f3a27a26089be6388eb62ee619a8ca1112200991d565daa04ca691901bc04238a8655e2c068039130e4c00027eac2675d9f4",
 "createdEventBlob": "CgMyLjEShwYKRQDVil8GHwhrPEtAW1fKCPTO/LfzonomCJvmOI62LuYZqMoREiAJkdVl2qBMppGQG8BCOKhlXiwGgDkTDkwAAn6sJnXZ9BIXdXRpbGl0eS1yZWdpc3RyeS1hcHAtdjAajQEKQDgyNzk4ZGYwMTgzMDE4NTI3MDRmMjEwYjk3YWRhYWJmNzZkM2VjZDM3ZDg4OWUxYmY5NmI1ZjMxYTIwZWVhMzQSB1V0aWxpdHkSCFJlZ2lzdHJ5EgNBcHASAlYwEgdTZXJ2aWNlEhFBbGxvY2F0aW9uRmFjdG9yeRoRQWxsb2NhdGlvbkZhY3RvcnkioQJqngIKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmClYKVDpSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgpsCmo6aGF1dGgwXzAwN2M2NWY4NTdmMWMzZDU5OWNiNmRmNzM3NzU6OjEyMjBkMmQ3MzJkMDQyYzI4MWNlZTgwZjQ4M2FiODBmM2NiYWE0NzgyODYwZWQ1ZjRkYzIyOGFiMDNkZWRkMmVlOGY5KlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmMmhhdXRoMF8wMDdjNjVmODU3ZjFjM2Q1OTljYjZkZjczNzc1OjoxMjIwZDJkNzMyZDA0MmMyODFjZWU4MGY0ODNhYjgwZjNjYmFhNDc4Mjg2MGVkNWY0ZGMyMjhhYjAzZGVkZDJlZThmOTlubOVh5DkGAEIqCiYKJAgBEiCdDhxHJbSFz7Snbvg8xLkPDPvaP3wl+HzTfq2LxHAGmRAe",
 "synchronizerId": ""
 },
 {
 "templateId": "3ca1343ab26b453d38c8adb70dca5f1ead8440c42b59b68f070786955cbf9ec1:Splice.Amulet:FeaturedAppRight",
 "contractId": "001c6e92181f8de9e4d15956e33f90db3085c518747de627134b6850459bf3662fca111220ee87bf1e3b05ed4d3f8a6c336290660f23409cb8d11a028e1073137eac8f78bf",
 "createdEventBlob": "CgMyLjESvQQKRQAcbpIYH43p5NFZVuM/kNswhcUYdH3mJxNLaFBFm/NmL8oREiDuh78eOwXtTT+KbDNikGYPI0CcuNEaAo4QcxN+rI94vxINc3BsaWNlLWFtdWxldBpkCkAzY2ExMzQzYWIyNmI0NTNkMzhjOGFkYjcwZGNhNWYxZWFkODQ0MGM0MmI1OWI2OGYwNzA3ODY5NTVjYmY5ZWMxEgZTcGxpY2USBkFtdWxldBoQRmVhdHVyZWRBcHBSaWdodCKqAWqnAQpNCks6SURTTzo6MTIyMGJlNThjMjllNjVkZTQwYmYyNzNiZTFkYzJiMjY2ZDQzYTlhMDAyZWE1YjE4OTU1YWVlZjdhYWM4ODFiYjQ3MWEKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmKklEU086OjEyMjBiZTU4YzI5ZTY1ZGU0MGJmMjczYmUxZGMyYjI2NmQ0M2E5YTAwMmVhNWIxODk1NWFlZWY3YWFjODgxYmI0NzFhMlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmOVDK9pNvQQYAQioKJgokCAESIOo7ddJGewmnI6M13zqEh5d8VRVxWJ73gao2y0uty955EB4=",
 "synchronizerId": ""
 },
 {
 "templateId": "ed73d5b9ab717333f3dbd122de7be3156f8bf2614a67360c3dd61fc0135133fa:Utility.Registry.V0.Configuration.Instrument:InstrumentConfiguration",
 "contractId": "00da61fcfa2d9b358c606f040a1d635fbabe4265d33908744a148a80be0dcdc383ca111220e86787467ef7be665f68b813a30de6b0480955dcb514ef29832720618375dee5",
 "createdEventBlob": "CgMyLjESnwkKRQDaYfz6LZs1jGBvBAodY1+6vkJl0zkIdEoUioC+Dc3Dg8oREiDoZ4dGfve+Zl9ouBOjDeawSAlV3LUU7ymDJyBhg3Xe5RITdXRpbGl0eS1yZWdpc3RyeS12MBqNAQpAZWQ3M2Q1YjlhYjcxNzMzM2YzZGJkMTIyZGU3YmUzMTU2ZjhiZjI2MTRhNjczNjBjM2RkNjFmYzAxMzUxMzNmYRIHVXRpbGl0eRIIUmVnaXN0cnkSAlYwEg1Db25maWd1cmF0aW9uEgpJbnN0cnVtZW50GhdJbnN0cnVtZW50Q29uZmlndXJhdGlvbiK9BWq6BQpsCmo6aGF1dGgwXzAwN2M2NWY4NTdmMWMzZDU5OWNiNmRmNzM3NzU6OjEyMjBkMmQ3MzJkMDQyYzI4MWNlZTgwZjQ4M2FiODBmM2NiYWE0NzgyODYwZWQ1ZjRkYzIyOGFiMDNkZWRkMmVlOGY5ClYKVDpSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKhAEKgQFqfwpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKCAoGQgRDQlRDChsKGUIXUmVnaXN0cmFySW50ZXJuYWxTY2hlbWUKigEKhwFahAEKgQFqfwpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKCAoGQgRDQlRDChsKGUIXUmVnaXN0cmFySW50ZXJuYWxTY2hlbWUKBAoCWgAKBAoCWgAKegp4UnYKdFpyCnBqbgpaClg6VmNidGMtYmVuZWZpY2lhcnk6OjEyMjBmYTg1NDNkYjZjNjZmZTNhNTViMWYxODBjOGRmYzdmODc2MjY1Yzc2Njg0ZmJjMWQzNWQ4OWUwMmM4YWFmZThlChAKDjIMMS4wMDAwMDAwMDAwKlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmMmhhdXRoMF8wMDdjNjVmODU3ZjFjM2Q1OTljYjZkZjczNzc1OjoxMjIwZDJkNzMyZDA0MmMyODFjZWU4MGY0ODNhYjgwZjNjYmFhNDc4Mjg2MGVkNWY0ZGMyMjhhYjAzZGVkZDJlZThmOTnz2t5E5kEGAEIqCiYKJAgBEiAb19AdEjIoV/7xtMY8A2/BkXnnQHGPcCNC0UEu/b5/YxAe",
 "synchronizerId": ""
 },
 {
 "templateId": "77df4e7b980c12de438d7b052141a762215fae790d81f71179c8fb534beb68f7:Utility.Credential.V0.Credential:Credential",
 "contractId": "0058feffeeaa48cc5526c723c4877af4f6abe3c76131c54ba0d63c6da299f8681bca111220b7032514b6b448d75ea6d9eefe01f0a345504e897a5f2e72fabf974322b20b07",
 "createdEventBlob": "CgMyLjESjQgKRQBY/v/uqkjMVSbHI8SHevT2q+PHYTHFS6DWPG2imfhoG8oREiC3AyUUtrRI116m2e7+AfCjRVBOiXpfLnL6v5dDIrILBxIVdXRpbGl0eS1jcmVkZW50aWFsLXYwGnMKQDc3ZGY0ZTdiOTgwYzEyZGU0MzhkN2IwNTIxNDFhNzYyMjE1ZmFlNzkwZDgxZjcxMTc5YzhmYjUzNGJlYjY4ZjcSB1V0aWxpdHkSCkNyZWRlbnRpYWwSAlYwEgpDcmVkZW50aWFsGgpDcmVkZW50aWFsIuwDaukDCloKWDpWaUJUQy12YWxpZGF0b3ItMTo6MTIyMGZhODU0M2RiNmM2NmZlM2E1NWIxZjE4MGM4ZGZjN2Y4NzYyNjVjNzY2ODRmYmMxZDM1ZDg5ZTAyYzhhYWZlOGUKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmChIKEEIOY2J0Yy1wcm92LWhhY2sKDgoMQgpXb3JrYXJvdW5kCgQKAlIACgQKAlIACoQBCoEBWn8KfWp7ClYKVEJSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgoTChFCD2hhc1JlZ2lzdHJ5Um9sZQoMCgpCCFByb3ZpZGVyCnwKemp4CnYKdGJyCnAKajpoYXV0aDBfMDA3YzY1Zjg1N2YxYzNkNTk5Y2I2ZGY3Mzc3NTo6MTIyMGQyZDczMmQwNDJjMjgxY2VlODBmNDgzYWI4MGYzY2JhYTQ3ODI4NjBlZDVmNGRjMjI4YWIwM2RlZGQyZWU4ZjkSAgoAKlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmKlZpQlRDLXZhbGlkYXRvci0xOjoxMjIwZmE4NTQzZGI2YzY2ZmUzYTU1YjFmMTgwYzhkZmM3Zjg3NjI2NWM3NjY4NGZiYzFkMzVkODllMDJjOGFhZmU4ZTJoYXV0aDBfMDA3YzY1Zjg1N2YxYzNkNTk5Y2I2ZGY3Mzc3NTo6MTIyMGQyZDczMmQwNDJjMjgxY2VlODBmNDgzYWI4MGYzY2JhYTQ3ODI4NjBlZDVmNGRjMjI4YWIwM2RlZGQyZWU4Zjk5iBIJ/7RABgBCKgomCiQIARIgwrTBnrlaL0STx5Hh0v7BEmbbCERCZDgwJWqqcljhQZ0QHg==",
 "synchronizerId": ""
 }
 ]
}'
```

***

## Additional Operations

The `cbtc-lib` library provides several utility modules for managing your CBTC holdings:

| Module                   | Purpose                                           |
| ------------------------ | ------------------------------------------------- |
| `cbtc::batch`            | Batch operations for sending CBTC from a CSV file |
| `cbtc::distribute`       | Distribute CBTC across multiple parties           |
| `cbtc::consolidate`      | Merge multiple UTXO holdings into fewer contracts |
| `cbtc::split`            | Split a single holding into multiple UTXOs        |
| `cbtc::active_contracts` | Query your current CBTC holdings                  |

***

## Troubleshooting

<details>

<summary>My deposit has not been minted after 90 minutes</summary>

* Verify the BTC transaction has at least 6 confirmations on a block explorer
* Confirm you sent to the correct deposit address (from Step 3)
* Check that your Canton participant node is connected and syncing
* Escalation: contact <support@bitsafe.finance>

</details>

<details>

<summary>Transfer offer is not appearing for the receiver</summary>

* The receiver must be registered in the DA Registry with a valid credential
* Confirm the receiver's Party ID is correct
* Check that both parties are connected to the same Canton sync domain

</details>

<details>

<summary>"Insufficient holdings" error when sending</summary>

* CBTC uses a UTXO model. You may need to consolidate holdings first using `cbtc::consolidate`
* Check your balance with `cbtc::active_contracts` to verify available amounts

</details>

<details>

<summary>Authentication token expired</summary>

* Keycloak tokens have a limited lifetime. Re-authenticate using Step 1 before retrying the operation

</details>

***

## Next Steps

* [**CBTC Minting and Burning**](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) - The same mint and burn flows in more depth, with error handling and recovery patterns for production
* [**API Reference**](https://docs.bitsafe.finance/developers/cbtc-api-reference) - Canton Ledger API endpoints, instrument IDs, rate limits, and error codes
* [**SDK Setup and Installation**](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) - Full `cbtc-lib` and `canton-lib` module reference
* [**Authentication Guide**](https://docs.bitsafe.finance/developers/cbtc-authentication) - Detailed Keycloak setup and an Auth0 community example
* [**Integration Guides**](https://docs.bitsafe.finance/developers/integration-guides) - Patterns for DeFi protocols, wallets, custody, and trading systems
* [**Withdraw via curl**](/developers/cbtc-quick-start/withdraw-curl) - The raw API withdrawal sequence, without the SDK

***

> 📧 **Need help?** Reach out to <support@bitsafe.finance>


# Withdraw curl

You can get the correct extraArgs and contract disclosures from the BitSafe API's `/cbtc/v1/token-standard-contracts` endpoint. So the contractIds, templateIds, and blobs in this example are just for example:

```bash
curl -X POST '${LEDGER_HOST}/v2/commands/submit-and-wait-for-transaction-tree' \
 --header 'Authorization: Bearer ${ACCESS_TOKEN}' \
 --data '{
 "commands": [
 {
 "ExerciseCommand": {
 "templateId": "#cbtc:CBTC.WithdrawAccount:CBTCWithdrawAccount",
 "contractId": "${WA_CID}",
 "choice": "CBTCWithdrawAccount_Withdraw",
 "choiceArgument": {
 "amount": "${AMOUNT}",
 "tokens": [
 "${INPUT_HOLDING}"
 ],
 "burnMintFactoryCid": "${ALLOCATION_FACTORY_CID}",
 "extraArgs": {
 "context": {
 "values": {
 "utility.digitalasset.com/instrument-configuration": {
 "tag": "AV_ContractId",
 "value": "00da61fcfa2d9b358c606f040a1d635fbabe4265d33908744a148a80be0dcdc383ca111220e86787467ef7be665f68b813a30de6b0480955dcb514ef29832720618375dee5"
 },
 "utility.digitalasset.com/app-reward-configuration": {
 "tag": "AV_ContractId",
 "value": "00bee23612f3c82dd6091e64ffde81cb535e7b446d7ebdf6d91329502c6023d1cdca1112209569dade5e20bf97f963882f6387293034a82f716d2b0df28820a82048f5f86c"
 },
 "utility.digitalasset.com/featured-app-right": {
 "tag": "AV_ContractId",
 "value": "001c6e92181f8de9e4d15956e33f90db3085c518747de627134b6850459bf3662fca111220ee87bf1e3b05ed4d3f8a6c336290660f23409cb8d11a028e1073137eac8f78bf"
 },
 "utility.digitalasset.com/issuer-credentials": {
 "tag": "AV_List",
 "value": [
 {
 "tag": "AV_ContractId",
 "value": "0058feffeeaa48cc5526c723c4877af4f6abe3c76131c54ba0d63c6da299f8681bca111220b7032514b6b448d75ea6d9eefe01f0a345504e897a5f2e72fabf974322b20b07"
 }
 ]
 }
 }
 },
 "meta": {
 "values": {
 "splice.lfdecentralizedtrust.org/reason": "CBTC Burn"
 }
 }
 }
 }
 }
 }
 ],
 "actAs": [
 "${OWNER_PARTY}"
 ],
 "commandId": "someCommandId",
 "disclosedContracts": [
 {
 "templateId": "82798df018301852704f210b97adaabf76d3ecd37d889e1bf96b5f31a20eea34:Utility.Registry.App.V0.Service.AllocationFactory:AllocationFactory",
 "contractId": "00d58a5f061f086b3c4b405b57ca08f4cefcb7f3a27a26089be6388eb62ee619a8ca1112200991d565daa04ca691901bc04238a8655e2c068039130e4c00027eac2675d9f4",
 "createdEventBlob": "CgMyLjEShwYKRQDVil8GHwhrPEtAW1fKCPTO/LfzonomCJvmOI62LuYZqMoREiAJkdVl2qBMppGQG8BCOKhlXiwGgDkTDkwAAn6sJnXZ9BIXdXRpbGl0eS1yZWdpc3RyeS1hcHAtdjAajQEKQDgyNzk4ZGYwMTgzMDE4NTI3MDRmMjEwYjk3YWRhYWJmNzZkM2VjZDM3ZDg4OWUxYmY5NmI1ZjMxYTIwZWVhMzQSB1V0aWxpdHkSCFJlZ2lzdHJ5EgNBcHASAlYwEgdTZXJ2aWNlEhFBbGxvY2F0aW9uRmFjdG9yeRoRQWxsb2NhdGlvbkZhY3RvcnkioQJqngIKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmClYKVDpSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgpsCmo6aGF1dGgwXzAwN2M2NWY4NTdmMWMzZDU5OWNiNmRmNzM3NzU6OjEyMjBkMmQ3MzJkMDQyYzI4MWNlZTgwZjQ4M2FiODBmM2NiYWE0NzgyODYwZWQ1ZjRkYzIyOGFiMDNkZWRkMmVlOGY5KlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmMmhhdXRoMF8wMDdjNjVmODU3ZjFjM2Q1OTljYjZkZjczNzc1OjoxMjIwZDJkNzMyZDA0MmMyODFjZWU4MGY0ODNhYjgwZjNjYmFhNDc4Mjg2MGVkNWY0ZGMyMjhhYjAzZGVkZDJlZThmOTlubOVh5DkGAEIqCiYKJAgBEiCdDhxHJbSFz7Snbvg8xLkPDPvaP3wl+HzTfq2LxHAGmRAe",
 "synchronizerId": ""
 },
 {
 "templateId": "3ca1343ab26b453d38c8adb70dca5f1ead8440c42b59b68f070786955cbf9ec1:Splice.Amulet:FeaturedAppRight",
 "contractId": "001c6e92181f8de9e4d15956e33f90db3085c518747de627134b6850459bf3662fca111220ee87bf1e3b05ed4d3f8a6c336290660f23409cb8d11a028e1073137eac8f78bf",
 "createdEventBlob": "CgMyLjESvQQKRQAcbpIYH43p5NFZVuM/kNswhcUYdH3mJxNLaFBFm/NmL8oREiDuh78eOwXtTT+KbDNikGYPI0CcuNEaAo4QcxN+rI94vxINc3BsaWNlLWFtdWxldBpkCkAzY2ExMzQzYWIyNmI0NTNkMzhjOGFkYjcwZGNhNWYxZWFkODQ0MGM0MmI1OWI2OGYwNzA3ODY5NTVjYmY5ZWMxEgZTcGxpY2USBkFtdWxldBoQRmVhdHVyZWRBcHBSaWdodCKqAWqnAQpNCks6SURTTzo6MTIyMGJlNThjMjllNjVkZTQwYmYyNzNiZTFkYzJiMjY2ZDQzYTlhMDAyZWE1YjE4OTU1YWVlZjdhYWM4ODFiYjQ3MWEKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmKklEU086OjEyMjBiZTU4YzI5ZTY1ZGU0MGJmMjczYmUxZGMyYjI2NmQ0M2E5YTAwMmVhNWIxODk1NWFlZWY3YWFjODgxYmI0NzFhMlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmOVDK9pNvQQYAQioKJgokCAESIOo7ddJGewmnI6M13zqEh5d8VRVxWJ73gao2y0uty955EB4=",
 "synchronizerId": ""
 },
 {
 "templateId": "ed73d5b9ab717333f3dbd122de7be3156f8bf2614a67360c3dd61fc0135133fa:Utility.Registry.V0.Configuration.Instrument:InstrumentConfiguration",
 "contractId": "00da61fcfa2d9b358c606f040a1d635fbabe4265d33908744a148a80be0dcdc383ca111220e86787467ef7be665f68b813a30de6b0480955dcb514ef29832720618375dee5",
 "createdEventBlob": "CgMyLjESnwkKRQDaYfz6LZs1jGBvBAodY1+6vkJl0zkIdEoUioC+Dc3Dg8oREiDoZ4dGfve+Zl9ouBOjDeawSAlV3LUU7ymDJyBhg3Xe5RITdXRpbGl0eS1yZWdpc3RyeS12MBqNAQpAZWQ3M2Q1YjlhYjcxNzMzM2YzZGJkMTIyZGU3YmUzMTU2ZjhiZjI2MTRhNjczNjBjM2RkNjFmYzAxMzUxMzNmYRIHVXRpbGl0eRIIUmVnaXN0cnkSAlYwEg1Db25maWd1cmF0aW9uEgpJbnN0cnVtZW50GhdJbnN0cnVtZW50Q29uZmlndXJhdGlvbiK9BWq6BQpsCmo6aGF1dGgwXzAwN2M2NWY4NTdmMWMzZDU5OWNiNmRmNzM3NzU6OjEyMjBkMmQ3MzJkMDQyYzI4MWNlZTgwZjQ4M2FiODBmM2NiYWE0NzgyODYwZWQ1ZjRkYzIyOGFiMDNkZWRkMmVlOGY5ClYKVDpSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKhAEKgQFqfwpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKCAoGQgRDQlRDChsKGUIXUmVnaXN0cmFySW50ZXJuYWxTY2hlbWUKigEKhwFahAEKgQFqfwpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKCAoGQgRDQlRDChsKGUIXUmVnaXN0cmFySW50ZXJuYWxTY2hlbWUKBAoCWgAKBAoCWgAKegp4UnYKdFpyCnBqbgpaClg6VmNidGMtYmVuZWZpY2lhcnk6OjEyMjBmYTg1NDNkYjZjNjZmZTNhNTViMWYxODBjOGRmYzdmODc2MjY1Yzc2Njg0ZmJjMWQzNWQ4OWUwMmM4YWFmZThlChAKDjIMMS4wMDAwMDAwMDAwKlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmMmhhdXRoMF8wMDdjNjVmODU3ZjFjM2Q1OTljYjZkZjczNzc1OjoxMjIwZDJkNzMyZDA0MmMyODFjZWU4MGY0ODNhYjgwZjNjYmFhNDc4Mjg2MGVkNWY0ZGMyMjhhYjAzZGVkZDJlZThmOTnz2t5E5kEGAEIqCiYKJAgBEiAb19AdEjIoV/7xtMY8A2/BkXnnQHGPcCNC0UEu/b5/YxAe",
 "synchronizerId": ""
 },
 {
 "templateId": "77df4e7b980c12de438d7b052141a762215fae790d81f71179c8fb534beb68f7:Utility.Credential.V0.Credential:Credential",
 "contractId": "0058feffeeaa48cc5526c723c4877af4f6abe3c76131c54ba0d63c6da299f8681bca111220b7032514b6b448d75ea6d9eefe01f0a345504e897a5f2e72fabf974322b20b07",
 "createdEventBlob": "CgMyLjESjQgKRQBY/v/uqkjMVSbHI8SHevT2q+PHYTHFS6DWPG2imfhoG8oREiC3AyUUtrRI116m2e7+AfCjRVBOiXpfLnL6v5dDIrILBxIVdXRpbGl0eS1jcmVkZW50aWFsLXYwGnMKQDc3ZGY0ZTdiOTgwYzEyZGU0MzhkN2IwNTIxNDFhNzYyMjE1ZmFlNzkwZDgxZjcxMTc5YzhmYjUzNGJlYjY4ZjcSB1V0aWxpdHkSCkNyZWRlbnRpYWwSAlYwEgpDcmVkZW50aWFsGgpDcmVkZW50aWFsIuwDaukDCloKWDpWaUJUQy12YWxpZGF0b3ItMTo6MTIyMGZhODU0M2RiNmM2NmZlM2E1NWIxZjE4MGM4ZGZjN2Y4NzYyNjVjNzY2ODRmYmMxZDM1ZDg5ZTAyYzhhYWZlOGUKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmChIKEEIOY2J0Yy1wcm92LWhhY2sKDgoMQgpXb3JrYXJvdW5kCgQKAlIACgQKAlIACoQBCoEBWn8KfWp7ClYKVEJSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgoTChFCD2hhc1JlZ2lzdHJ5Um9sZQoMCgpCCFByb3ZpZGVyCnwKemp4CnYKdGJyCnAKajpoYXV0aDBfMDA3YzY1Zjg1N2YxYzNkNTk5Y2I2ZGY3Mzc3NTo6MTIyMGQyZDczMmQwNDJjMjgxY2VlODBmNDgzYWI4MGYzY2JhYTQ3ODI4NjBlZDVmNGRjMjI4YWIwM2RlZGQyZWU4ZjkSAgoAKlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmKlZpQlRDLXZhbGlkYXRvci0xOjoxMjIwZmE4NTQzZGI2YzY2ZmUzYTU1YjFmMTgwYzhkZmM3Zjg3NjI2NWM3NjY4NGZiYzFkMzVkODllMDJjOGFhZmU4ZTJoYXV0aDBfMDA3YzY1Zjg1N2YxYzNkNTk5Y2I2ZGY3Mzc3NTo6MTIyMGQyZDczMmQwNDJjMjgxY2VlODBmNDgzYWI4MGYzY2JhYTQ3ODI4NjBlZDVmNGRjMjI4YWIwM2RlZGQyZWU4Zjk5iBIJ/7RABgBCKgomCiQIARIgwrTBnrlaL0STx5Hh0v7BEmbbCERCZDgwJWqqcljhQZ0QHg==",
 "synchronizerId": ""
 },
 {
 "templateId": "ed73d5b9ab717333f3dbd122de7be3156f8bf2614a67360c3dd61fc0135133fa:Utility.Registry.V0.Configuration.AppReward:AppRewardConfiguration",
 "contractId": "00bee23612f3c82dd6091e64ffde81cb535e7b446d7ebdf6d91329502c6023d1cdca1112209569dade5e20bf97f963882f6387293034a82f716d2b0df28820a82048f5f86c",
 "createdEventBlob": "CgMyLjESigcKRQC+4jYS88gt1gkeZP/egctTXntEbX699tkTKVAsYCPRzcoREiCVadreXiC/l/ljiC9jhykwNKgvcW0rDfKIIKggSPX4bBITdXRpbGl0eS1yZWdpc3RyeS12MBqLAQpAZWQ3M2Q1YjlhYjcxNzMzM2YzZGJkMTIyZGU3YmUzMTU2ZjhiZjI2MTRhNjczNjBjM2RkNjFmYzAxMzUxMzNmYRIHVXRpbGl0eRIIUmVnaXN0cnkSAlYwEg1Db25maWd1cmF0aW9uEglBcHBSZXdhcmQaFkFwcFJld2FyZENvbmZpZ3VyYXRpb24iqgNqpwMKbApqOmhhdXRoMF8wMDdjNjVmODU3ZjFjM2Q1OTljYjZkZjczNzc1OjoxMjIwZDJkNzMyZDA0MmMyODFjZWU4MGY0ODNhYjgwZjNjYmFhNDc4Mjg2MGVkNWY0ZGMyMjhhYjAzZGVkZDJlZThmOQpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYK3gEK2wFq2AEKTQpLOklEU086OjEyMjBiZTU4YzI5ZTY1ZGU0MGJmMjczYmUxZGMyYjI2NmQ0M2E5YTAwMmVhNWIxODk1NWFlZWY3YWFjODgxYmI0NzFhCoYBCoMBaoABCmwKajpoYXV0aDBfMDA3YzY1Zjg1N2YxYzNkNTk5Y2I2ZGY3Mzc3NTo6MTIyMGQyZDczMmQwNDJjMjgxY2VlODBmNDgzYWI4MGYzY2JhYTQ3ODI4NjBlZDVmNGRjMjI4YWIwM2RlZGQyZWU4ZjkKEAoOMgwwLjIwMDAwMDAwMDAqaGF1dGgwXzAwN2M2NWY4NTdmMWMzZDU5OWNiNmRmNzM3NzU6OjEyMjBkMmQ3MzJkMDQyYzI4MWNlZTgwZjQ4M2FiODBmM2NiYWE0NzgyODYwZWQ1ZjRkYzIyOGFiMDNkZWRkMmVlOGY5MlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmOTNRkpGtQQYAQioKJgokCAESIEkSmOztxETzHu7k7YoYrhYmnA4xZxW6uqMAl1xkvmiOEB4=",
 "synchronizerId": ""
 }
 ]
}'
```


# CBTC Testnet Guide

> ⚠️ **API Disclaimer:** CBTC APIs are subject to change. Testnet behavior may differ from mainnet in some respects (see Parity section below).

***

## Overview: CBTC Testnet for Developers

The CBTC testnet is a sandbox environment where developers can experiment with the full mint, burn, and transfer lifecycle using **test BTC** with no real funds at risk. We recommend all integrations start on testnet before deploying to mainnet.

***

## How to Get Testnet CBTC: Three Options

### Option 1: CBTC Testnet Faucet (Recommended)

The fastest way to get testnet tokens:

[**CBTC Testnet Faucet →**](https://cbtc-faucet.bitsafe.finance/)

Simply enter your testnet wallet address and receive testnet CBTC and CC (for gas) instantly.

> 💡 **Quick and easy:** No setup required. Just enter your address and go.

### Option 2: Bron Wallet Testnet Environment

If the faucet is unavailable or you want a full testnet wallet environment:

1. **Create a new workspace** in [Bron Wallet](https://bron.app/)
2. Enable **Developer settings → Testnet mode** during workspace creation
3. **Create a testnet account** (toggle Testnet ON in account settings)
4. Select a **Trusted third party** (e.g., Qrypt) for key recovery
5. Use the faucet to fund your new testnet account

### Option 3: Mint via Testnet Flow

You can also mint testnet CBTC through the same flow as mainnet, using testnet BTC. This is useful for testing the full minting integration:

1. Set up your participant pointing at the **testnet** Canton network
2. Install CBTC DAR files
3. Follow the standard minting flow (see [Minting and Burning Guide](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning))
4. Use testnet BTC from a Bitcoin testnet faucet

***

## Testnet Environment Details

| Property                  | Testnet                                                                                             | Mainnet                                                                             |
| ------------------------- | --------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------- |
| **Registry URL**          | [`https://api.utilities.digitalasset-staging.com`](https://api.utilities.digitalasset-staging.com/) | [`https://api.utilities.digitalasset.com`](https://api.utilities.digitalasset.com/) |
| **Coordinator URL**       | [`https://testnet.dlc.link/attestor-1`](https://testnet.dlc.link/attestor-1)                        | [`https://mainnet.dlc.link/attestor-1`](https://mainnet.dlc.link/attestor-1)        |
| **Instrument ID (admin)** | `cbtc-network::12201b17...508f`                                                                     | `cbtc-network::12205af3...b262`                                                     |
| **BTC network**           | Bitcoin Testnet                                                                                     | Bitcoin Mainnet                                                                     |
| **Faucet**                | [cbtc-faucet.bitsafe.finance](https://cbtc-faucet.bitsafe.finance/)                                 | N/A (real BTC required)                                                             |

### Testnet Instrument ID (Full)

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-staging.com"
}
```

***

## Testnet vs. Mainnet: What Is the Same and What Differs

> 📋 Understanding what is the same and what differs between testnet and mainnet is critical for a smooth production launch.

### ✅ What Is Identical

* **DAR files:** Same CBTC Daml packages
* **API surface:** Same Canton Ledger API endpoints and Daml template interfaces
* **Mint and burn flows:** Same step-by-step process
* **Governance model:** Same Attestor threshold approval mechanism
* **Token standard:** CIP-56 compliant on both networks

### ⚠️ What Differs

* **Attestor set:** Testnet runs a **smaller** Attestor set than mainnet
* **Confirmation times:** May be faster on testnet due to less Bitcoin network congestion
* **Instrument IDs:** Different across networks - always fetch from the metadata URL, never hardcode
* **BTC:** Testnet uses test BTC with no real value
* **Faucet availability:** Testnet has a faucet; mainnet requires real BTC

### 🚫 What Is Mocked or Unavailable on Testnet

* **Real BTC settlement:** No real Bitcoin is involved
* **Production Attestor SLAs:** Testnet Attestors do not carry the same uptime guarantees
* **Mainnet fee structure:** Fees on testnet may not reflect production costs

***

## Important Operational Notes

> ⚠️ **Testnet may be reset without notice.** Do not rely on testnet state for production planning. Testnet CBTC balances and transaction history may not persist across resets.

* Testnet is for **development and testing only**
* Do not use testnet data for compliance, reporting, or production decisions
* Testnet performance is not indicative of mainnet performance

***

## Migrate from CBTC Testnet to Mainnet: Step-by-Step Checklist

When your testnet integration is working, the migration to mainnet involves:

1. **Update your participant config** to point at the mainnet Canton network
2. **Update Instrument IDs** to mainnet values (see [API Reference](https://docs.bitsafe.finance/developers/cbtc-api-reference))
3. **Update Coordinator URL** to [`https://mainnet.dlc.link/attestor-1`](https://mainnet.dlc.link/attestor-1)
4. **Use real BTC** for minting - the flow is identical
5. **Review authentication** - ensure your production OIDC provider is configured
6. **Test with a small amount first** - mint a minimal amount of CBTC on mainnet before going live

***

## Devnet

There is also a **devnet** environment for earlier-stage experimentation. Devnet is less stable than testnet and may be updated more frequently.

**Coordinator URL:** [`https://devnet.dlc.link/attestor-2`](https://devnet.dlc.link/attestor-2)

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-dev.com"
}
```

***

## Troubleshooting

| Issue                                 | Resolution                                                                    |
| ------------------------------------- | ----------------------------------------------------------------------------- |
| Faucet not working                    | Use Bron Wallet testnet setup (Option 2) or contact <support@bitsafe.finance> |
| Testnet CBTC balance disappeared      | Testnet may have been reset - request new tokens from the faucet              |
| Minting on testnet takes too long     | Check Bitcoin testnet block times - they can be irregular                     |
| Cannot connect to testnet participant | Verify your participant config points to the correct testnet endpoints        |

**Support:** <support@bitsafe.finance>

***


# CBTC Minting and Burning

> ⚠️ **API Disclaimer:** CBTC APIs are subject to change. There is no formal versioning policy today. Breaking changes are communicated via the site changelog.

***

## Overview: The Full BTC to CBTC Lifecycle

This guide covers the complete lifecycle of converting Bitcoin to CBTC and back: minting (BTC to CBTC on Canton) and burning (CBTC back to BTC). For a quick end-to-end walkthrough, see the [CBTC Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start). This guide goes deeper into each step, covering edge cases, error handling, and recovery patterns for production integrations.

> 🛠️ **Prerequisite: install the SDK.** The Rust examples on this page use the `cbtc-lib` SDK. See [SDK Setup and Installation](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) for installing `cbtc-lib` and `canton-lib`, uploading the CBTC DAR files, and configuring your environment.

**Key facts:**

* **Exchange rate:** 1 BTC = 1 CBTC, always
* **Confirmations required:** 6 Bitcoin block confirmations (\~60 minutes)
* **Processing time:** Additional 60-120 seconds after confirmations for Attestor verification
* **Wallet requirement:** Taproot-compatible Bitcoin wallet (P2TR addresses)
* **Transaction limits:** 0.0001 BTC minimum, 5 BTC maximum by default - set per account and adjustable on request (see below)
* **Minter credential:** Required before you can create a deposit or withdraw account (see below)

***

## Transaction Limits

Mint and burn amounts are bounded by **per-account limits**. The defaults are:

| Limit       | Default    |
| ----------- | ---------- |
| **Minimum** | 0.0001 BTC |
| **Maximum** | 5 BTC      |

> 💡 **Limits are adjustable.** These are defaults, not fixed protocol constraints. If your integration needs a different range, contact <sales@bitsafe.finance> to have your account limits modified.

### Read limits from the account, do not hardcode them

Because limits are set per account and can be changed on request, **read them at runtime rather than hardcoding the defaults**. They are carried on the Deposit Account (for minting) and the Withdraw Account (for burning), and are returned by the deposit account status call:

```rust
use cbtc::mint_redeem::mint;

let status = mint::get_deposit_account_status(mint::GetDepositAccountStatusParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
 api_url: api_url.clone(),
 account_contract_id: deposit_account.contract_id.clone(),
}).await?;

if let Some(limits) = &status.limits {
 println!("Min: {:?} | Max: {:?}", limits.min_amount, limits.max_amount);
}
```

Both fields are optional. `None` means that bound is not enforced for the account:

```rust
pub struct Limits {
 pub min_amount: Option<DamlDecimal>, // serialised as "minAmount"
 pub max_amount: Option<DamlDecimal>, // serialised as "maxAmount"
}
```

### Validate before submitting

`cbtc::mint_redeem::models::check_limits` validates an amount against a set of limits locally, so an out-of-range request fails in your code instead of being rejected downstream:

```rust
use cbtc::mint_redeem::models::check_limits;

check_limits("Withdraw", amount.clone(), &withdraw_account.limits)?;
```

It returns a descriptive error - `"Withdraw amount 0.00001 is below minimum 0.0001"` or `"... exceeds maximum 5"` - and succeeds when no limits are set.

***

## Prerequisite: Obtain a Minter Credential

> ⚠️ **Minting and burning require a Minter credential.** This is a hard requirement, not an optional step. Creating a deposit account or a withdraw account will fail without one. Transferring, receiving, and holding CBTC do **not** require a credential — only minting and burning do.

A Minter credential is a Daml contract issued to your Canton party by the **CBTC registrar**. It carries a claim with the property `hasCBTCRole` and the value `Minter`, and you pass its contract ID into the account-creation calls.

### How to request one

Minter credentials are issued as part of commercial onboarding. To request one, contact the BitSafe team at <sales@bitsafe.finance> with your Canton Party ID and target environment (testnet or mainnet).

### Check whether you already hold one

Once the registrar has issued your credential, use the `cbtc::credentials` module to find it. A credential is a Minter credential if any of its claims has `property == "hasCBTCRole"` and `value == "Minter"`:

```rust
use cbtc::credentials::{list_credentials, ListCredentialsParams};

let credentials = list_credentials(ListCredentialsParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
}).await?;

let minter_credential_cids: Vec<String> = credentials
 .iter()
 .filter(|c| {
 c.claims
 .iter()
 .any(|claim| claim.property == "hasCBTCRole" && claim.value == "Minter")
 })
 .map(|c| c.contract_id.clone())
 .collect();

if minter_credential_cids.is_empty() {
 return Err("No Minter credential found for this party".into());
}
```

### Accept a pending credential offer

The registrar issues the credential as an **offer** that your party must accept before it becomes active. If `list_credentials` returns nothing, check for a pending offer and accept it:

```rust
use cbtc::credentials::{
 accept_credential_offer, find_user_service, list_credential_offers,
 AcceptCredentialOfferParams, FindUserServiceParams, ListCredentialOffersParams,
};

let user_service = find_user_service(FindUserServiceParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
}).await?;

let offers = list_credential_offers(ListCredentialOffersParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
}).await?;

accept_credential_offer(AcceptCredentialOfferParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
 user_service_contract_id: user_service.contract_id.clone(),
 user_service_template_id: user_service.template_id.clone(),
 credential_offer_cid: offers[0].contract_id.clone(),
}).await?;
```

> ℹ️ **Accepting a credential is permanent.** It creates a persistent on-ledger contract with no archive choice, so a credential cannot be un-accepted. Accept only the offer you actually intend to use.

A complete runnable version of this flow is in the library's [`credentials` example](https://github.com/DLC-link/cbtc-lib/blob/v0.6.4/examples/credentials.rs).

***

## How to Mint CBTC: Deposit Bitcoin and Receive Wrapped BTC on Canton

### How It Works

```mermaid
sequenceDiagram
 participant Dev as Your App
 participant Canton as Canton Ledger API
 participant BTC as Bitcoin Network
 participant Att as Attestor Network

 Dev->>Canton: 1. Authenticate (get JWT)
 Dev->>Canton: 2. Create Deposit Account
 Canton-->>Dev: Deposit Account ID
 Dev->>Canton: 3. Request BTC Deposit Address
 Canton-->>Dev: Taproot address (P2TR)
 Dev->>BTC: 4. Send BTC to address
 BTC-->>Att: 5. Attestors monitor for 6 confirmations
 Att->>Canton: 6. Submit ConfirmDepositAction (threshold)
 Canton-->>Dev: 7. CBTC minted to your party
```

### Step-by-Step

Step 1: Authenticate

Obtain a JWT token from your OIDC provider (Keycloak is officially supported). See the [Authentication Guide](https://docs.bitsafe.finance/developers/cbtc-authentication) for setup details.

Step 2: Create a Deposit Account

A Deposit Account is required before you can generate deposit addresses. This call requires the Minter credential contract IDs obtained in the prerequisite step above.

**Using cbtc-lib (Rust):**

```rust
use cbtc::mint_redeem::{mint, attestor};

// First get account rules from the Attestor
let account_rules = attestor::get_account_contract_rules(&api_url).await?;

let deposit_account = mint::create_deposit_account(mint::CreateDepositAccountParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 account_rules,
 credential_cids: minter_credential_cids.clone(),
}).await?;

println!("Deposit Account ID: {}", deposit_account.contract_id);
```

**Using Canton API (curl):**

You can fetch the CBTCDepositAccountRules from the BitSafe API's `/cbtc/v1/account-contract-rules` endpoint

> ⚠️ **A Minter credential is required.** The `CreateDepositAccount` choice takes your Minter credential contract IDs as an argument. See [Prerequisite: Obtain a Minter Credential](#prerequisite-obtain-a-minter-credential) above. Requests without a valid credential are rejected.

```bash
curl -X POST '${LEDGER_HOST}/v2/commands/submit-and-wait-for-transaction-tree' \
 --header 'Authorization: Bearer ${ACCESS_TOKEN}' \
 --data '{
 "commands": [
 {
 "ExerciseCommand": {
 "templateId": "#cbtc:CBTC.DepositAccount:CBTCDepositAccountRules",
 "contractId": "${DA_RULES_CID}",
 "choice": "CBTCDepositAccountRules_CreateDepositAccount",
 "choiceArgument": {
 "owner" : "${OWNER_PARTY}"
 }
 }
 }
 ],
 "actAs": [
 "${OWNER_PARTY}"
 ],
 "commandId": "someCommandID",
 "disclosedContracts": [
 {
 "templateId": "#cbtc:CBTC.DepositAccount:CBTCDepositAccountRules",
 "contractId": "${DA_RULES_CID}",
 "createdEventBlob": "${DA_RULES_BLOB}",
 "synchronizerId": ""
 }
 ]
}'
```

{% hint style="info" %}
Note: The submit-and-wait-for-transaction-tree endpoint is deprecated in Canton 3.5 but remains functional on 3.5.1. Consider migrating to submit-and-wait-for-transaction for new integrations.
{% endhint %}

Step 3: Generate a Bitcoin Deposit Address

Each deposit address is unique to your account and is a standard **Taproot (P2TR)** address.

**Using cbtc-lib (Rust):**

```rust
use cbtc::mint_redeem::mint;

let btc_address = mint::get_bitcoin_address(mint::GetBitcoinAddressParams {
 api_url: api_url.clone(),
 account_id: deposit_account.contract_id.clone(),
}).await?;

println!("Send BTC to: {}", btc_address);
```

Step 4: Send Bitcoin

Send the exact amount of BTC you want to mint as CBTC to the generated Taproot address from your Bitcoin wallet.

Step 5: Wait for Confirmations

The Attestor network automatically monitors the Bitcoin network. Once your transaction reaches **6 confirmations** (\~60 minutes), it transitions to the processing state.

You can poll for deposit status:

**Using cbtc-lib (Rust):**

```rust
use cbtc::mint_redeem::mint;

let status = mint::get_deposit_account_status(mint::GetDepositAccountStatusParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
 api_url: api_url.clone(),
 account_contract_id: deposit_account.contract_id.clone(),
}).await?;

println!("Bitcoin address: {} | Last processed block: {}",
 status.bitcoin_address, status.last_processed_bitcoin_block);
```

Step 6: Attestor Verification

This step is fully automated. The Attestor network:

1. Independently verifies the Bitcoin transaction has 6+ confirmations
2. Each Attestor submits a `ConfirmDepositAction` to the Canton governance module
3. Once the required threshold of confirmations is reached, the Coordinator executes the mint **No action is required from your application during this step.**

Step 7: CBTC Available

Your CBTC is minted and available in your Canton party. Check your balance:

**Using cbtc-lib (Rust):**

```rust
use cbtc::active_contracts;

let holdings = active_contracts::get(active_contracts::Params {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
}).await?;

println!("CBTC holdings: {} contract(s)", holdings.len());
```

***

## How to Burn CBTC: Redeem Wrapped Bitcoin for Native BTC

### How It Works

```mermaid
sequenceDiagram
 participant Dev as Your App
 participant Canton as Canton Ledger API
 participant Att as Attestor Network
 participant BTC as Bitcoin Network

 Dev->>Canton: 1. Create WithdrawAccount (set BTC destination address)
 Dev->>Canton: 2. Submit withdrawal against WithdrawAccount
 Canton->>Att: 3. Attestors verify and approve withdrawal
 Att->>Att: 4. FROST threshold signing of BTC transaction
 Att->>BTC: 5. Broadcast signed transaction
 BTC-->>Dev: 6. BTC arrives after 6 confirmations
```

### Step-by-Step

Step 1: Initiate a Burn

First, create a **WithdrawAccount** with your destination BTC address. The destination address is stored on the WithdrawAccount and can be updated later. Then submit the withdrawal against that account. Like deposit account creation, this requires your Minter credential contract IDs.

**Using cbtc-lib (Rust):**

```rust
use cbtc::mint_redeem::redeem;

// Step 1: Create a withdraw account
let withdraw_account = redeem::create_withdraw_account(redeem::CreateWithdrawAccountParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 account_rules_contract_id: rules.wa_rules.contract_id.clone(),
 account_rules_template_id: rules.wa_rules.template_id.clone(),
 account_rules_created_event_blob: rules.wa_rules.created_event_blob.clone(),
 destination_btc_address: btc_destination_address.clone(),
 credential_cids: minter_credential_cids.clone(),
}).await?;

// Step 2: Submit the withdrawal (burns CBTC, Attestor network processes BTC payout)
let updated_account = redeem::submit_withdraw(redeem::SubmitWithdrawParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 api_url: api_url.clone(),
 withdraw_account_contract_id: withdraw_account.contract_id.clone(),
 amount: cbtc::DamlDecimal::parse("0.001")?,
 holding_contract_ids: holding_ids,
 credential_cids: Some(minter_credential_cids.clone()),
}).await?;

println!("Withdrawal submitted. Pending balance: {}", updated_account.pending_balance);
```

> ℹ️ **Amounts are `DamlDecimal`.** Build them with `cbtc::DamlDecimal::parse`, which validates the value against Daml's decimal precision rules up front, so an unrepresentable amount fails locally instead of being rejected by the ledger. This applies to transfer and allocation amounts too.

Step 2: Attestor Verification and Signing

The Attestor network:

1. Verifies the burn request on Canton
2. Constructs the Bitcoin withdrawal transaction
3. Coordinates FROST threshold signing across Attestors
4. Once the signing threshold is met, broadcasts the signed transaction to the Bitcoin network **This step is fully automated. No action required.**

Step 3: Bitcoin Delivery

After the signed transaction is broadcast, wait for 6 Bitcoin confirmations. Your BTC will arrive at the specified destination address.

***

## Error Handling and Recovery Patterns for CBTC Integrations

> 🔧 **Error handling is critical for production integrations.** The CBTC system includes built-in resilience, but your application should handle these scenarios gracefully.

### Failed Broadcast

The system includes **automatic retry logic**. If a Bitcoin transaction fails to broadcast initially, the Coordinator detects the failure during subsequent periodic checks (every 60-120 seconds) and rebroadcasts using stored transaction data.

**What your app should do:** Monitor withdrawal status. If status remains in `broadcasting` for more than 10 minutes, log an alert for investigation.

### Insufficient Confirmations

If a deposit stalls below 6 confirmations (e.g., due to Bitcoin network congestion), the system simply waits. There is no timeout.

**What your app should do:** Display the current confirmation count to the user. Consider showing an estimated time based on current Bitcoin block times.

### Idempotency

Each withdrawal generates a **unique transaction ID** that prevents accidental double-spending, even if network issues cause retry attempts. The system is designed to be idempotent.

**What your app should do:** Store the withdrawal request ID and use it for status checks rather than initiating duplicate requests.

### Attestor Timeout

If governance approval is delayed (e.g., some Attestors are temporarily offline), the system continues to collect approvals. As long as the threshold can eventually be met, the operation will complete.

**What your app should do:** If a mint or burn is pending for more than 2 hours, escalate to BitSafe support.

### Partial Failure

If some Attestors approve but the threshold is not reached (e.g., too many Attestors offline simultaneously), the operation will remain pending until the threshold is met or the situation is resolved.

**What your app should do:** Alert your operations team. Contact <support@bitsafe.finance>.

***

## CBTC UTXO Management: Consolidation and Best Practices

> ⚠️ **Important for high-volume integrations.** Each CBTC transfer creates UTXOs. Canton recommends a maximum of **10 UTXOs per party**. Exceeding this causes increased load and fees on your node.

The cbtc-lib Rust library provides functions for managing UTXOs:

```rust
use cbtc::consolidate;

// Check UTXO count and consolidate if threshold exceeded
let result = consolidate::check_and_consolidate(consolidate::CheckConsolidateParams {
 party: party_id.clone(),
 threshold: 10, // Canton's soft limit
 ledger_host: ledger_host.clone(),
 access_token: access_token.clone(),
 registry_url: registry_url.clone(),
 decentralized_party_id: decentralized_party_id.clone(),
}).await?;

if result.consolidated {
 println!("Consolidated {} UTXOs into {}", result.utxos_before, result.utxos_after);
}
```

**Best practices:**

* Monitor UTXO count per party and consolidate proactively
* Batch transfers where possible to minimise UTXO creation
* If creating many parties, use the Ledger API directly (not wallet UI/API) - see [Canton docs](https://docs.digitalasset.com/build/3.4/tutorials/json-api/canton_and_the_json_ledger_api_ts.html#allocating-a-party)

***

## Escalation Path

| Situation                 | Action                                                                          |
| ------------------------- | ------------------------------------------------------------------------------- |
| Mint pending > 2 hours    | Check Bitcoin confirmations first. If 6+ confirmations reached, contact BitSafe |
| Burn pending > 2 hours    | Contact BitSafe engineering                                                     |
| Unexpected error from API | Retry with exponential backoff. If persistent, contact BitSafe                  |
| UTXO-related issues       | Use cbtc-lib consolidation functions. If unresolved, contact BitSafe            |

**Support channels:**

* **Email:** <support@bitsafe.finance>

***


# CBTC Authentication

> ⚠️ **API Disclaimer:** CBTC APIs are subject to change. Authentication flows may evolve as Canton's identity layer matures.

***

## Overview: How Authentication Works for CBTC on Canton

All CBTC operations go through the Canton Ledger API, which requires a valid **JWT (JSON Web Token)** for every request. The JWT is issued by an **OIDC (OpenID Connect) provider** connected to your Canton participant node.

This guide covers two authentication options for developers building with CBTC and the Canton Network:

* **Keycloak** (officially supported by BitSafe)
* **Auth0** (community example, not officially maintained) For deeper background on how Canton handles authentication and authorization at the platform level, see the [Canton Authorization Documentation](https://docs.digitalasset.com/build/3.4/sdlc-howtos/applications/secure/authorization.html).

***

## CBTC Authentication Flow: JWT and OIDC

```mermaid
sequenceDiagram
 participant App as Your Application
 participant OIDC as OIDC Provider<br>(Keycloak / Auth0)
 participant Canton as Canton Participant<br>(Ledger API)

 App->>OIDC: 1. Request token (client credentials or auth code)
 OIDC-->>App: 2. JWT access token
 App->>Canton: 3. API call with Bearer token
 Canton-->>App: 4. Response
```

***

## Set Up Keycloak for CBTC Authentication (Officially Supported) ✅

Keycloak is the **officially supported** OIDC provider for CBTC integrations. BitSafe engineering provides support for Keycloak-based authentication.

### Prerequisites

* Keycloak instance running and accessible
* A realm configured for your Canton participant
* A client application registered in Keycloak

### Step 1: Register a Client

In your Keycloak admin console:

1. Navigate to your realm → **Clients** → **Create client**
2. Set **Client type** to `OpenID Connect`
3. Set **Client ID** (e.g., `cbtc-minting-app`)
4. Enable **Client authentication** (for server-to-server flows)
5. Under **Service account roles**, enable as needed

### Step 2: Configure Your Canton Participant

Your Canton participant must be configured to trust your OIDC provider. Participant configuration is complex and environment-specific. Refer to the official validator operator documentation:

[**Canton Validator Operator Guide →**](https://docs.dev.sync.global/validator_operator/index.html)

### Step 3: Obtain a Token

**Client Credentials flow** (for server-to-server / backend integrations):

```bash
curl -X POST "https://<your-keycloak>/auth/realms/<your-realm>/protocol/openid-connect/token" \
 -H "Content-Type: application/x-www-form-urlencoded" \
 -d "grant_type=client_credentials" \
 -d "client_id=cbtc-minting-app" \
 -d "client_secret=$CLIENT_SECRET"
```

**Password grant flow** (for user-facing / interactive applications):

```bash
curl -X POST "https://<your-keycloak>/auth/realms/<your-realm>/protocol/openid-connect/token" \
 -H "Content-Type: application/x-www-form-urlencoded" \
 -d "grant_type=password" \
 -d "client_id=cbtc-minting-app" \
 -d "username=$KEYCLOAK_USERNAME" \
 -d "password=$KEYCLOAK_PASSWORD"
```

**Response** (both flows):

```json
{
 "access_token": "eyJhbGciOiJSUzI1NiIs...",
 "expires_in": 300,
 "token_type": "Bearer"
}
```

### Step 4: Use the Token

Include the token in all Canton Ledger API calls:

```bash
curl -X POST "https://<your-participant>/v2/state/active-contracts" \
 -H "Authorization: Bearer $ACCESS_TOKEN" \
 -H "Content-Type: application/json" \
 -d '{... }'
```

### Token Refresh

Tokens expire (typically 5 minutes for Keycloak). Your application should:

1. Cache the token until near expiry
2. Request a new token before the current one expires
3. Retry failed requests with a fresh token if you receive a `401`

***

## Set Up Auth0 for CBTC Authentication (Community Example) ⚠️

> 💡 **Auth0 compatibility.** Both Keycloak and Auth0 follow the OAuth2/OIDC standard, so the login flow and token usage are identical. There is one known caveat: Auth0 requires an extra `audience` parameter in the token request. The `cbtc-lib` and `canton-lib` libraries **do not pass this parameter by default**, so they won't work out of the box with Auth0. This is a straightforward fix on either the library side or the client side. See the workaround below. BitSafe engineering support covers **Keycloak-based authentication only**. For Auth0-specific configuration issues, refer to [Auth0's documentation](https://auth0.com/docs).

### Prerequisites

* Auth0 tenant and API configured
* Application registered as **Machine to Machine** (for backend) or **Single Page Application** (for frontend)

### Step 1: Create an Auth0 API

In the Auth0 dashboard:

1. Navigate to **Applications** → **APIs** → **Create API**
2. Set **Name** (e.g., `Canton Ledger API`)
3. Set **Identifier** to your participant's Ledger API URL
4. Set **Signing Algorithm** to `RS256`

### Step 2: Register a Machine-to-Machine Application

1. Navigate to **Applications** → **Create Application**
2. Select **Machine to Machine Applications**
3. Authorise the application to call your Canton Ledger API
4. Note the **Client ID** and **Client Secret**

### Step 3: Configure Your Canton Participant

Point your participant to Auth0's JWKS endpoint. Participant configuration is complex and environment-specific. Refer to the official validator operator documentation:

[**Canton Validator Operator Guide →**](https://docs.dev.sync.global/validator_operator/index.html)

### Step 4: Obtain a Token

```bash
curl -X POST "https://<your-auth0-domain>/oauth/token" \
 -H "Content-Type: application/json" \
 -d '{
 "client_id": "'$CLIENT_ID'",
 "client_secret": "'$CLIENT_SECRET'",
 "audience": "https://<your-participant>/v2/",
 "grant_type": "client_credentials"
 }'
```

> ⚠️ **The `audience` parameter is required for Auth0.** This is the key difference from Keycloak. Without it, Auth0 will return an opaque token that the Canton participant will reject. Set `audience` to your participant's Ledger API base URL. **If using cbtc-lib / canton-lib:** The Rust libraries' `keycloak::login::password` and `keycloak::login::client_credentials` functions do not pass an `audience` parameter. To use Auth0, you'll need to either:
>
> 1. Make the token request directly via HTTP (as shown above) instead of using the library helper
> 2. Patch the login functions to include the `audience` field, which is a small change A library-level fix may be shipped in a future release of `canton-lib`.

### Step 5: Use the Token

Same as Keycloak. Include the Bearer token in all API requests.

***

## Wallet-Based Authentication for Canton dApps

For applications that use Canton-compatible wallets (Loop, Console/Zoro, Bron), authentication is handled by the wallet provider. Your application receives a JWT through the wallet's SDK or connect flow.

Supported wallets:

* **Loop Wallet**
* **Console / Zoro Wallet**
* **Bron Wallet**
* **WalletConnect** (for dApp integrations)
* **Node login** (direct participant authentication) See the [Integration Guides](https://docs.bitsafe.finance/developers/integration-guides) for wallet-specific connection patterns.

***

## Troubleshooting

| Issue                               | Cause                                            | Resolution                                                                |
| ----------------------------------- | ------------------------------------------------ | ------------------------------------------------------------------------- |
| `401 Unauthorized` on every request | JWT not trusted by participant                   | Verify JWKS URL in participant config matches your OIDC provider          |
| Token expires immediately           | Clock skew between OIDC provider and participant | Sync system clocks (NTP)                                                  |
| CORS errors in browser              | Ingress not configured for CORS                  | Add CORS annotations to your ingress - see Minting App Installation Guide |
| `invalid_grant` from OIDC provider  | Client secret rotated or incorrect               | Regenerate and update client secret                                       |

***

## JWT Security Best Practices for Canton Applications

* **Never expose client secrets** in frontend code. Use the Client Credentials flow only from backend services.
* **Rotate secrets regularly.** Update client secrets in both your OIDC provider and your application config.
* **Use short-lived tokens.** The default 5-minute expiry is appropriate for most use cases.
* **Restrict party access.** Configure your JWT claims to limit which Canton parties a token can act as.

***


# CBTC API Reference

> ⚠️ **API Stability Notice:** All endpoints and interfaces are subject to change without notice. There is no formal versioning policy today. Breaking changes are communicated via the site changelog.

***

## CBTC SDK Reference: cbtc-lib (Rust)

For most integrations, we recommend using **cbtc-lib** (Rust) rather than raw API calls:

* **Repository:** [github.com/DLC-link/cbtc-lib](https://github.com/DLC-link/cbtc-lib)
* **Current version:** v0.6.4
* **Crate name:** `cbtc` (add via `cbtc = { git = "ssh://git@github.com/DLC-link/cbtc-lib.git", tag = "v0.6.4" }`)
* **Lower-level library:** [github.com/DLC-link/canton-lib](https://github.com/DLC-link/canton-lib) (v0.6.1)
* **Code examples:** [github.com/DLC-link/cbtc-lib/tree/main/examples](https://github.com/DLC-link/cbtc-lib/tree/main/examples)
* **Setup guide:** [SDK Setup and Installation](https://docs.bitsafe.finance/developers/sdk-setup-and-installation)

***

## Overview: Canton Ledger API for CBTC Operations

All CBTC operations (minting, burning, transferring wrapped Bitcoin) are performed through the **Canton Ledger API** (also called the JSON Ledger API). There is no separate "CBTC API." You interact with CBTC by exercising choices on Daml smart contracts running on your Canton participant node.

**Base URL:** `https://<your-participant-host>/v2/`

**Authentication:** Bearer token (JWT) from your OIDC provider. See the [Authentication Guide](https://docs.bitsafe.finance/developers/cbtc-authentication).

**Content-Type:** `application/json` for all requests.

***

## Prerequisites

Before calling any CBTC API:

1. **Canton participant node** running and connected to the network
2. **CBTC DAR files** installed on your participant - [download from GitHub](https://github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars)
3. **Valid JWT** from your OIDC provider (Keycloak officially supported)
4. **Party ID** allocated on your participant

***

## Canton Ledger API Endpoints

For full endpoint documentation covering the Canton Ledger API (including all endpoints used by CBTC operations), refer to the official Canton documentation:

[**Canton JSON Ledger API Documentation →**](https://docs.digitalasset.com/build/3.4/explanations/json-api/index.html)

***

## CBTC Instrument ID Management: Devnet, Testnet, and Mainnet

CBTC uses the Canton Token Standard. To interact with CBTC programmatically, you need the correct **Instrument ID** for your target network.

> ⚠️ **Instrument IDs differ across networks** (devnet, testnet, mainnet). Always fetch the latest from the metadata URL rather than hardcoding.

### Devnet

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-dev.com"
}
```

**Metadata:** [View](https://api.utilities.digitalasset-dev.com/api/token-standard/v0/registrars/cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff/registry/metadata/v1/instruments)

### Testnet

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-staging.com"
}
```

**Metadata:** [View](https://api.utilities.digitalasset-staging.com/api/token-standard/v0/registrars/cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f/registry/metadata/v1/instruments)

### Mainnet

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12205af3b949a04776fc48cdcc05a060f6bda2e470632935f375d1049a8546a3b262",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset.com"
}
```

**Metadata:** [View](https://api.utilities.digitalasset.com/api/token-standard/v0/registrars/cbtc-network::12205af3b949a04776fc48cdcc05a060f6bda2e470632935f375d1049a8546a3b262/registry/metadata/v1/instruments)

**Token Standard API Reference:** [Canton Token Standard Docs](https://docs.dev.sync.global/app_dev/token_standard/index.html#api-references)

> 💡 **Polling pattern:** Instrument IDs can change due to network dynamics (e.g., DAR upgrades). Query the metadata URL periodically rather than hardcoding values. There is currently no push notification for ID changes - this is a known gap.

***

## Rate Limits

There are no BitSafe-imposed rate limits on the Canton Ledger API. However:

* **Canton network throughput:** Transfers take a few seconds each. Approximately 500 transfers per 10-minute period is near the current practical limit.
* **Your participant node:** Performance depends on your infrastructure. Monitor node resource usage under load.

***

## API Error Handling for CBTC Operations

| Error               | Cause                               | Resolution                              |
| ------------------- | ----------------------------------- | --------------------------------------- |
| `401 Unauthorized`  | Invalid or expired JWT              | Re-authenticate with your OIDC provider |
| `404 Not Found`     | Contract ID no longer active        | Re-query for current contract IDs       |
| `409 Conflict`      | Duplicate command ID                | Use a unique `commandId` per request    |
| UTXO limit exceeded | Too many UTXOs for a party (max 10) | Consolidate UTXOs using cbtc-lib        |

***


# Instrument ID Management

***

## What Are Instrument IDs?

Every token on Canton is identified by an **Instrument ID**, a combination of an **admin** party ID and a token **id** string, plus a **registry URL**. These values let any CIP-56-compliant tool discover and interact with CBTC.

***

## Why IDs Change

Instrument IDs can change due to network dynamics, including DAR upgrades, network migrations, or infrastructure changes. **Never hardcode Instrument IDs.** Fetch them dynamically from the metadata URL.

> ⚠️ There is currently **no push notification** when Instrument IDs change. Poll the metadata URL periodically.

***

## Current IDs by Network

### Devnet

* **Registry URL:** [`https://api.utilities.digitalasset-dev.com`](https://api.utilities.digitalasset-dev.com/)
* **Coordinator URL:** [`https://devnet.dlc.link/attestor-2`](https://devnet.dlc.link/attestor-2)
* **Metadata:** [View](https://api.utilities.digitalasset-dev.com/api/token-standard/v0/registrars/cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff/registry/metadata/v1/instruments)

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-dev.com"
}
```

### Testnet

* **Registry URL:** [`https://api.utilities.digitalasset-staging.com`](https://api.utilities.digitalasset-staging.com/)
* **Coordinator URL:** [`https://testnet.dlc.link/attestor-1`](https://testnet.dlc.link/attestor-1)
* **Metadata:** [View](https://api.utilities.digitalasset-staging.com/api/token-standard/v0/registrars/cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f/registry/metadata/v1/instruments)

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-staging.com"
}
```

### Mainnet

* **Registry URL:** [`https://api.utilities.digitalasset.com`](https://api.utilities.digitalasset.com/)
* **Coordinator URL:** [`https://mainnet.dlc.link/attestor-1`](https://mainnet.dlc.link/attestor-1)
* **Metadata:** [View](https://api.utilities.digitalasset.com/api/token-standard/v0/registrars/cbtc-network::12205af3b949a04776fc48cdcc05a060f6bda2e470632935f375d1049a8546a3b262/registry/metadata/v1/instruments)

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12205af3b949a04776fc48cdcc05a060f6bda2e470632935f375d1049a8546a3b262",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset.com"
}
```

***

## Recommended Polling Pattern

```rust
use std::time::Duration;

// Poll every 5 minutes in production
const POLL_INTERVAL: Duration = Duration::from_secs(300);

async fn refresh_instrument_id(registry_url: &str, admin: &str) -> Result<InstrumentId> {
 let url = format!(
 "{}/api/token-standard/v0/registrars/{}/registry/metadata/v1/instruments",
 registry_url, admin
 );
 let response = reqwest::get(&url).await?.json::<InstrumentMetadata>().await?;
 Ok(response.instrument_id)
}
```

**Best practices:**

* Cache the Instrument ID locally and refresh on a schedule (every 5-15 minutes)
* Log a warning if the ID changes between polls, as this may indicate a DAR upgrade
* On startup, always fetch fresh rather than relying on cached values
* Handle fetch failures gracefully and use the last known good value

***

## Token Standard API Reference

Full documentation for the Canton Token Standard API: [Canton Token Standard Docs](https://docs.dev.sync.global/app_dev/token_standard/index.html#api-references)

**Requirements:** CBTC is CIP-56 compliant. No special requirements for holding CBTC.

***


# Integration Guides

> ⚠️ **API Disclaimer:** CBTC APIs are subject to change. Label all examples with the SDK version and DAR version they were tested against.

***

## Overview

This page provides integration patterns for common CBTC use cases. Each pattern includes architecture notes, key considerations, and pointers to relevant code. For API details, see the [API Reference](https://docs.bitsafe.finance/developers/cbtc-api-reference). For authentication setup, see the [Authentication Guide](https://docs.bitsafe.finance/developers/cbtc-authentication).

***

## Integration Pattern 1: DeFi Protocol

**Use case:** Build a DEX, lending platform, or liquidity pool using CBTC as collateral.

### Architecture

1. Your protocol runs on a Canton participant node with CBTC DAR files installed
2. Users deposit CBTC into your protocol's Canton party via a `Transfer` choice
3. Your protocol logic (Daml contracts) manages positions, collateral, and settlement
4. Users withdraw CBTC back to their own party when exiting

### Key Considerations

* **UTXO management:** Each transfer creates UTXOs. Keep below 10 per party. Use `cbtc-lib` consolidation functions.
* **Instrument ID:** Fetch dynamically - see [Instrument ID Management](https://docs.bitsafe.finance/developers/instrument-id-management)
* **Privacy:** Canton transactions are private by default. Only parties to a contract see its details. This eliminates MEV.
* **Transfer costs:** \~$3-5 per CBTC transfer on Canton currently. Factor this into your protocol economics.

### Example Partners

* **Bron** - BTC-CBTC and CC-CBTC swapping on Canton
* **Elk Capital Markets / Triangle** - OTC and app-based CBTC trading
* **Silvana** - DEX/trading venue on Canton *(coming soon)*

***

## Integration Pattern 2: Wallet or Custody Solution

**Use case:** Support CBTC in an institutional-grade wallet or custody platform.

### Architecture

1. Wallet connects to a Canton participant via the Ledger API
2. Authentication via OIDC (Keycloak supported, Auth0 community example available)
3. CBTC balances queried via `state-queries` endpoint
4. Transfers executed via `Transfer` choice on CBTC token contracts

### Supported Wallets (Current Ecosystem)

* **Loop Wallet** - Canton-native wallet with CBTC support
* **Console / Zoro Wallet** - Canton wallet with API access
* **Bron Wallet** - Multi-party wallet with testnet support
* **WalletConnect** - For dApp-to-wallet connections

### Key Considerations

* **External signing:** Available for integration with custody providers (DFNS, Fordefi, Ledger)
* **Party creation at scale:** If creating 10+ parties, use the Ledger API directly rather than wallet UI - see [Canton docs](https://docs.digitalasset.com/build/3.4/tutorials/json-api/canton_and_the_json_ledger_api_ts.html#allocating-a-party)
* **CORS:** If your wallet makes browser-based API calls, configure CORS on your ingress

***

## Integration Pattern 3: Trading System

**Use case:** Build spot trading, perpetual contracts, options, or structured products with CBTC.

### Why Canton for Trading

* **No public mempool** - positions are not visible to other participants, eliminating front-running and sandwich attacks (MEV)
* **Private transactions** - only parties to a trade see the details
* **Audit-ready** - Canton's privacy model supports selective disclosure for compliance

### Architecture

1. Trading engine runs as Daml contracts on Canton
2. CBTC used as settlement or collateral asset
3. Counterparty discovery and matching handled by your protocol
4. Settlement is atomic - either both sides complete or neither does

### Example: Options on CBTC

CBTC holders can write covered CALL options, earning premium income while maintaining BTC exposure. Settlement uses Canton's atomic dual-token transfer - the buyer receives the underlying asset while the seller receives payment, atomically.

### DvP Settlement Using Allocations

For atomic delivery-versus-payment, `cbtc-lib` provides the `cbtc::allocation` module, which implements the Canton Token Standard allocation lifecycle. This is the mechanism behind the atomic settlement described above.

**How it differs from a standard transfer.** The two-phase `transfer` / `accept` flow described in the [Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start) is **free-of-payment (FOP)**: the sender offers CBTC, the receiver accepts, and nothing is exchanged in return. There is no linkage to a second leg. An **allocation** instead locks CBTC into one leg of a multi-leg settlement that a third party settles atomically, so the CBTC only moves if the other leg moves too.

|                        | FOP transfer (`cbtc::transfer` + `cbtc::accept`) | DvP allocation (`cbtc::allocation`)                   |
| ---------------------- | ------------------------------------------------ | ----------------------------------------------------- |
| **Parties**            | Sender, receiver                                 | Sender, receiver, **settlement executor** (the venue) |
| **Settled by**         | The receiver, by accepting                       | The executor, across all legs at once                 |
| **Atomicity**          | Single leg only                                  | All legs settle together or none do                   |
| **Sender can reclaim** | Cancel the offer (`cbtc::cancel_offers`)         | Withdraw the allocation before settlement             |
| **Deadlines**          | `execute_before`                                 | `allocate_before`, then `settle_before`               |

**Lifecycle.** The sender locks their leg, then the executor settles:

1. **Allocate** - the leg sender calls `cbtc::allocation::allocate`, which exercises `AllocationFactory_Allocate` and locks the sender's holdings. If no input holdings are specified, the library auto-selects them.
2. **Execute** - the settlement executor calls `cbtc::allocation::execute_transfer` (`Allocation_ExecuteTransfer`). A coordinating app normally settles every leg together in a single transaction; the library exposes the single-leg choice for that purpose.
3. **Or unwind** - the sender can call `cbtc::allocation::withdraw` (`Allocation_Withdraw`) to reclaim locked holdings before settlement, and `cbtc::allocation::cancel` (`Allocation_Cancel`) releases them back to the sender.

**Timing.** An allocation must be funded before `allocate_before` and settled before `settle_before`, which must be the later of the two.

Allocating CBTC into a settlement leg:

```rust
use cbtc::allocation;

let allocation_spec = common::allocation::AllocationSpecification {
 settlement: common::allocation::SettlementInfo {
 executor: executor_party_id.clone(), // the venue settling the legs
 settlement_ref: common::allocation::Reference {
 id: settlement_ref_id.clone(),
 cid: None,
 },
 requested_at: now.to_rfc3339(),
 allocate_before: (now + chrono::Duration::hours(24)).to_rfc3339(),
 settle_before: (now + chrono::Duration::hours(48)).to_rfc3339(),
 meta: common::allocation::Metadata::default(),
 },
 transfer_leg_id: "leg0".to_string(),
 transfer_leg: common::allocation::TransferLeg {
 sender: sender_party_id.clone(),
 receiver: receiver_party_id.clone(),
 amount: cbtc::DamlDecimal::parse("0.1")?,
 instrument_id: common::transfer::InstrumentId {
 admin: decentralized_party_id.clone(),
 id: "CBTC".to_string(),
 },
 meta: common::allocation::Metadata::default(),
 },
};

allocation::allocate(allocation::Params {
 allocation: allocation_spec,
 requested_at: now.to_rfc3339(),
 input_holding_cids: Vec::new(), // empty = library auto-selects the sender's holdings
 ledger_host: ledger_host.clone(),
 access_token: access_token.clone(),
 registry_url: registry_url.clone(),
 decentralized_party_id: decentralized_party_id.clone(),
}).await?;
```

Reclaiming an allocation before settlement:

```rust
use cbtc::allocation;

allocation::withdraw(allocation::ActionParams {
 allocation_contract_id: allocation_cid.clone(),
 actor_party: sender_party_id.clone(),
 ledger_host: ledger_host.clone(),
 access_token: access_token.clone(),
 registry_url: registry_url.clone(),
 decentralized_party_id: decentralized_party_id.clone(),
}).await?;
```

> 💡 **No Minter credential needed.** Allocations move existing CBTC rather than creating or destroying it, so they do not require the Minter credential that minting and burning do.

A complete runnable example is in the library: [`examples/allocate_cbtc.rs`](https://github.com/DLC-link/cbtc-lib/blob/v0.6.4/examples/allocate_cbtc.rs). For the underlying standard, see the [Canton Token Standard allocation docs](https://docs.dev.sync.global/app_dev/token_standard/index.html).

***

## Integration Pattern 4: Minting Integration

**Use case:** Offer CBTC minting as a service to your users.

### Three Options

| Option                           | Description                                               | Effort                    |
| -------------------------------- | --------------------------------------------------------- | ------------------------- |
| **1. Direct API**                | Install CBTC DAR, call Canton APIs to mint/redeem         | Low - a few hours         |
| **2. Self-hosted UI**            | Install DAR + BitSafe minting UI locally                  | Medium - more maintenance |
| **3. Hosted UI** *(coming soon)* | Use BitSafe's centrally hosted UI against your validator. | TBD                       |

For Option 1, see the [Minting and Burning Guide](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) and [API Reference](https://docs.bitsafe.finance/developers/cbtc-api-reference).

For Options 2 and 3, contact BitSafe for setup details.

***

## Getting Started

1. **Install the SDK and DAR files** - see [SDK Setup and Installation](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) for `cbtc-lib`, `canton-lib`, DAR upload, and environment configuration
2. **Set up testnet first** - see [Testnet Guide](https://docs.bitsafe.finance/developers/cbtc-testnet-guide)
3. **Mint your first CBTC** - see [Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start)
4. **Review examples** - [GitHub examples](https://github.com/DLC-link/cbtc-lib/tree/main/examples) **Need help?** Reach out via <support@bitsafe.finance>

***


# Technical Reference

> ⚠️

***

## Token Details

| Property                | Value                                                                                                      |
| ----------------------- | ---------------------------------------------------------------------------------------------------------- |
| **Name**                | CBTC (Canton Bitcoin)                                                                                      |
| **Standard**            | CIP-56 (Canton Instrument Protocol)                                                                        |
| **Backing**             | 1:1 with native BTC                                                                                        |
| **Network**             | Canton Network                                                                                             |
| **Deposit requirement** | Taproot-compatible Bitcoin wallet (P2TR)                                                                   |
| **Transaction limits**  | 0.0001 BTC minimum, 5 BTC maximum by default. Set per account and adjustable on request                    |
| **Confirmations**       | 6 Bitcoin blocks (\~60 minutes)                                                                            |
| **Audit**               | [Quantstamp](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html) |

***

## Network Environments

| Environment | Registry URL                                                                                        | Coordinator URL                                                              | Bitcoin Network |
| ----------- | --------------------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------- | --------------- |
| **Devnet**  | [`https://api.utilities.digitalasset-dev.com`](https://api.utilities.digitalasset-dev.com/)         | [`https://devnet.dlc.link/attestor-2`](https://devnet.dlc.link/attestor-2)   | Bitcoin Testnet |
| **Testnet** | [`https://api.utilities.digitalasset-staging.com`](https://api.utilities.digitalasset-staging.com/) | [`https://testnet.dlc.link/attestor-1`](https://testnet.dlc.link/attestor-1) | Bitcoin Testnet |
| **Mainnet** | [`https://api.utilities.digitalasset.com`](https://api.utilities.digitalasset.com/)                 | [`https://mainnet.dlc.link/attestor-1`](https://mainnet.dlc.link/attestor-1) | Bitcoin Mainnet |

For full Instrument IDs per network, see [Instrument ID Management](https://docs.bitsafe.finance/developers/instrument-id-management).

***

## Canton Network Requirements

To interact with CBTC you need:

1. **Canton participant node** - connected to the target network (devnet/testnet/mainnet)
2. **CBTC DAR files** - installed on your participant. All versions must be installed to access all live contract versions.

* Download: [github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars](https://github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars) (latest DAR: `cbtc-1.2.1`)

1. **OIDC provider** - Keycloak (officially supported) or Auth0 (community example)
2. **Canton CLI** - version 3.3.0+ for DAR upload scripts
3. **Prerequisites for CLI:** `jq`, `curl`, `java` (11+)

### DAR Upload

```bash
git clone https://github.com/DLC-link/cbtc-lib
cd cbtc-lib
# Edit misc/connect.conf to point to your participant
canton run 00_UploadDars.sc -c./misc/connect.conf
```

The upload script is **idempotent** - safe to re-run.

***

## Fee Structure

> ✅ **Confirmed: Mint and burn fees are 0%.** There are no BitSafe fees on CBTC mint or burn operations.

### Canton Transfer Costs

* CBTC transfers on Canton cost approximately **$3-5 per transaction** (network gas, not BitSafe fees)
* Cost varies based on payload size and UTXO count
* Sending CBTC is generally more expensive than sending Canton Coin (CC) due to larger payload

***

## GitHub Repositories

| Repository     | Version      | Description                                         | Link                                                                 |
| -------------- | ------------ | --------------------------------------------------- | -------------------------------------------------------------------- |
| **cbtc-lib**   | `v0.6.4`     | Rust SDK for CBTC operations (mint, burn, transfer) | [GitHub](https://github.com/DLC-link/cbtc-lib)                       |
| **canton-lib** | `v0.6.1`     | Lower-level Canton interaction library              | [GitHub](https://github.com/DLC-link/canton-lib/)                    |
| **CBTC DAR**   | `cbtc-1.2.1` | Daml packages, upload scripts, connect config       | [GitHub](https://github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars) |

**Note:** The crate name is `cbtc`. DAR versions and crate versions are numbered independently: `cbtc-lib` v0.6.4 ships DAR `cbtc-1.2.1`.

***

## Transfer Speed

* Canton transfers take **a few seconds each**
* Practical throughput: \~**500 transfers per 10-minute period**
* UTXO limit: **10 UTXOs per party** (Canton recommendation). Exceeding this increases load and fees.

***

## External Links

* [CBTC Technical Documentation (live site)](https://docs.bitsafe.finance/bitsafe-documentation/product-suite/cbtc)
* [Canton Network](https://www.canton.network/)
* [Canton Developer Docs](https://docs.digitalasset.com/)
* [FROST Whitepaper](https://eprint.iacr.org/2020/852)
* [Quantstamp Audit Report](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html)
* [Canton Whitepaper](https://www.canton.network/whitepapers)
* [Chainlink Proof of Reserve (CBTC)](https://data.chain.link/)

***


# Security Deep Dive

***

## Overview

CBTC's security model is built on three pillars: **FROST threshold signatures** on the Bitcoin side, a **decentralised Attestor Network** bridging both chains, and **Daml smart contracts** governing all operations on Canton. This page covers each in detail.

***

## FROST Threshold Signatures

CBTC uses **FROST** (Flexible Round-Optimised Schnorr Threshold Signatures), a cryptographic protocol formalised in [Komlo & Goldberg, 2020](https://eprint.iacr.org/2020/852) and enabled on Bitcoin via the **Taproot** upgrade.

### How FROST Works

FROST is a **two-round signing protocol:**

1. **Round One (Commitment):** The Coordinator selects the message to be signed and the set of participating Attestors. Each Attestor generates fresh nonces and public commitments, sent to the Coordinator.
2. **Round Two (Signature Share):** The Coordinator broadcasts all commitments. Each Attestor verifies them, computes an individual signature share, and sends it back. The Coordinator aggregates shares into a single valid Schnorr signature.

### Why FROST for CBTC

* **Taproot-native:** FROST signatures are standard Schnorr signatures, compatible with any Taproot (P2TR) wallet. No special wallet support needed.
* **Indistinguishable on-chain:** A FROST threshold signature looks identical to a single-signer Schnorr signature. No one can determine from the blockchain that a threshold scheme was used.
* **Smaller and cheaper:** One aggregated signature regardless of threshold size, versus N signatures for traditional on-chain multisig. Lower transaction fees.
* **No single point of failure:** The signing key is never reconstructed. Each Attestor holds only a share.

### Security Properties

* **Unforgeability:** No coalition below the threshold can produce a valid signature, even with adaptive corruption (formally proven in the ePrint paper)
* **Robustness against forgery attacks:** FROST mitigates certain Schnorr-specific threshold forgery vectors
* **Forget-and-Forgive protection:** The resharing protocol includes acknowledgement steps preventing split-group attacks during key rotation **Full paper:** [FROST: Flexible Round-Optimized Schnorr Threshold Signatures (ePrint 2020/852)](https://eprint.iacr.org/2020/852)

***

## Attestor Network

The Attestor Network is the decentralised security backbone of CBTC.

### Composition

* **3 external node operators** (Finoa, Nethermind, DSRV)
* **1 BitSafe-operated node** (4 total)
* Each Attestor runs nodes on **both** the Bitcoin and Canton networks

### Responsibilities

Attestor responsibilities are **almost entirely automated:**

* Independent verification of Bitcoin transactions reaching 6 confirmations
* Submission of `ConfirmDepositAction` (for mints) and `ArchiveWithdrawRequest` (for burns) to the Canton governance module
* Participation in FROST threshold signing for Bitcoin withdrawal transactions
* Monitoring deposit accounts and withdrawal requests The only manual process is **governance** - adding or removing Attestor nodes, which requires coordination between operators.

### Threshold Governance

* For critical actions (minting, burning), each Attestor submits confirmation **independently**
* Confirmations are recorded as Canton contracts
* Once the number of valid confirmations meets the **predefined threshold**, the Coordinator executes the action
* **No single party** - including BitSafe or the Coordinator - can unilaterally mint, burn, or move BTC

### Coordinator Role

The Coordinator is a service (which can be an Attestor or a separate non-signing entity) that:

* Executes periodic checks every **60-120 seconds**
* Monitors deposit accounts for new Bitcoin transactions
* Constructs Bitcoin transactions for withdrawals
* Submits governance actions to Canton
* Coordinates the FROST signing rounds **The Coordinator cannot act unilaterally.** It facilitates the process but requires threshold approval for every action.

***

## Dual-Network Security Model

CBTC's security spans two networks simultaneously:

| Layer                           | Network    | Security Mechanism                         |
| ------------------------------- | ---------- | ------------------------------------------ |
| **Bitcoin custody**             | Bitcoin L1 | FROST threshold signatures (Taproot)       |
| **Governance and coordination** | Canton     | Daml contracts with threshold confirmation |
| **Token operations**            | Canton     | CIP-56 compliant Daml contracts            |

The same Attestor network secures both layers, creating seamless security across both blockchains.

***

## Reliability and Safeguards

### Automatic Retry

If a Bitcoin transaction fails to broadcast, the Coordinator detects the failure during subsequent checks and rebroadcasts using stored transaction data.

### Idempotent Operations

Each withdrawal generates a unique transaction ID preventing double-spending, even with network-induced retries.

### Distributed Verification

No single Attestor can block or manipulate operations. The threshold system ensures continued operation even with some nodes offline.

***

## Trust and Threat Model

The CBTC system assumes an honest majority of the Attestor network Key trust assumptions:

* A threshold of Attestors must be honest and online for the system to operate
* The Coordinator facilitates but cannot act unilaterally
* BitSafe operates one Attestor node but has no special privileges
* Canton's privacy model ensures transaction details are visible only to involved parties

### What Cannot Happen

* No single party (including BitSafe) can mint CBTC without genuine BTC deposits
* No single party can withdraw BTC without threshold approval
* No front-running or MEV - Canton has no public mempool

***

## Audit Reports

CBTC smart contracts have been audited by **Quantstamp:**

[**View Full Audit Report →**](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html)

***

## Further Reading

* [FROST Whitepaper (ePrint 2020/852)](https://eprint.iacr.org/2020/852)
* [Canton Network Whitepaper](https://www.canton.network/whitepapers)
* [Canton Token Standard Docs](https://docs.dev.sync.global/app_dev/token_standard/index.html#api-references)

***


# Resources

***

## Glossary

| Term                        | Definition                                                                                                                                      |
| --------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------- |
| **CBTC**                    | Canton Bitcoin - a 1:1 wrapped BTC token on the Canton Network, issued and redeemed via a decentralised bridge.                                 |
| **Canton Network**          | A permissioned blockchain built by Digital Asset for institutional finance. Private transactions, no public mempool.                            |
| **CIP-56**                  | Canton Instrument Protocol - the token standard CBTC complies with, enabling interoperability with any CIP-56-compliant tool.                   |
| **Daml**                    | The smart contract language used on Canton. CBTC operations are Daml contract choices.                                                          |
| **DAR file**                | Daml Archive - a compiled Daml package that you install on your Canton participant to interact with CBTC contracts.                             |
| **FROST**                   | Flexible Round-Optimised Schnorr Threshold Signatures - the cryptographic protocol securing CBTC's Bitcoin custody.                             |
| **Attestor**                | An independent node operator that verifies Bitcoin transactions and participates in threshold signing for CBTC mint/burn operations.            |
| **Coordinator**             | A service that facilitates Attestor coordination, monitors deposits, and constructs Bitcoin transactions. Cannot act unilaterally.              |
| **Minter**                  | A credential granting the right to create deposit accounts and initiate CBTC minting.                                                           |
| **Instrument ID**           | The unique identifier for CBTC on a given Canton network (devnet/testnet/mainnet). Differs per environment.                                     |
| **Taproot (P2TR)**          | A Bitcoin address type introduced with the Taproot upgrade. Required for CBTC deposit addresses.                                                |
| **UTXO**                    | Unspent Transaction Output. Each CBTC transfer creates UTXOs. Canton recommends max 10 per party.                                               |
| **Decentralized Party**     | A Canton-native construct where multiple independent operators collectively control a party via threshold signing.                              |
| **ERC-4626**                | A tokenised vault standard. BitSafe Vaults implement ERC-4626 semantics on Canton.                                                              |
| **Curator**                 | A professional asset manager who operates yield strategies within a BitSafe Vault.                                                              |
| **LP (Liquidity Provider)** | An institutional depositor who provides capital to a Vault in exchange for shares and yield.                                                    |
| **MEV**                     | Maximal Extractable Value - front-running and sandwich attacks possible on public blockchains. Canton eliminates this via private transactions. |

***

## GitHub Repositories

* **cbtc-lib** (Rust SDK) - [github.com/DLC-link/cbtc-lib](https://github.com/DLC-link/cbtc-lib)
* **canton-lib** (lower-level Canton library) - [github.com/DLC-link/canton-lib](https://github.com/DLC-link/canton-lib)
* **cbtc-lib** (DAR files, scripts) - [github.com/DLC-link/cbtc-lib](https://github.com/DLC-link/cbtc-lib)
* **Code examples** - [github.com/DLC-link/cbtc-lib/tree/main/examples](https://github.com/DLC-link/cbtc-lib/tree/main/examples)

***

## Audit Reports

* [**Quantstamp Audit Report (CBTC)**](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html)

***

## Whitepapers and Research

* [**FROST: Flexible Round-Optimized Schnorr Threshold Signatures**](https://eprint.iacr.org/2020/852) - Komlo & Goldberg, 2020
* [**Canton Network Whitepaper**](https://www.canton.network/whitepapers) - Digital Asset

***

## Canton Ecosystem Links

* [Canton Network](https://www.canton.network/)
* [Canton Developer Documentation](https://docs.digitalasset.com/)
* [Canton Token Standard API](https://docs.dev.sync.global/app_dev/token_standard/index.html#api-references)
* [BitSafe Technical Docs (live site)](https://docs.bitsafe.finance/bitsafe-documentation/product-suite/cbtc)

***

## Support

> 📬 **Developer support:** <support@bitsafe.finance>

***

## Changelog

***


# Changelog

All notable changes to the CBTC developer documentation are logged here. This includes new pages, content updates, API changes, SDK version bumps, and corrections.

***

## 2026-02-10

### 🚀 Initial publication

* Published first draft of all CBTC developer documentation across 11 pages
* **New pages:** CBTC Overview, Quick Start, Minting and Burning, API Reference, Authentication, Integration Guides, Security Deep Dive, Technical Reference, Instrument ID Management, SDK Setup and Installation, Testnet Guide
* **SDK:** Documentation pinned to `cbtc-lib` v0.0.1 (post-December 2025 restructure)
* **Instrument IDs:** Published devnet, testnet, and mainnet IDs with metadata endpoint URLs
* **Known gaps:** Vaults documentation (Not Started), Home landing page (in progress), Error Codes Reference (deferred to v2)

***

## 2026-03-02

### 🔧 PR #22: Code and API corrections across all CBTC docs

Applied all corrections from [GitHub PR #22](https://github.com/DLC-link/cbtc-lib/pull/22) ("Fix CBTC docs to match actual cbtc-lib and canton-lib APIs"). Every Rust code example, curl command, module path, and function signature has been verified against the actual `cbtc` v0.3.0 and `canton-lib` v0.3.0 source code.

**Affected pages:** Quick Start, Minting and Burning, API Reference, Authentication, SDK Setup, Technical Reference

**Version and crate updates**

* SDK version updated from v0.0.1 to **v0.3.0** across all pages
* Crate name corrected from `cbtc-lib` / `cbtc_lib` to **`cbtc`**
* `canton-lib` documented as a **workspace** with 4 crates: `keycloak`, `ledger`, `registry`, `common` (all v0.3.0) **Authentication code**
* All auth examples updated from `keycloak::login(url, id, secret, user, pass)` to struct-based `keycloak::login::password(PasswordParams {... })` and `keycloak::login::client_credentials(ClientCredentialsParams {... })`
* Auth0 callout updated to reference correct function names (`keycloak::login::password`, `keycloak::login::client_credentials`) **Module paths and function names**
* `cbtc_lib::deposit` → `cbtc::mint_redeem::mint`
* `cbtc_lib::balance` → `cbtc::active_contracts`
* `cbtc_lib::withdraw` → `cbtc::mint_redeem::redeem`
* `cbtc_lib::utxo` → `cbtc::consolidate`
* `get_deposit_address` → `get_bitcoin_address`
* `get_active_contracts` → `active_contracts::get`
* `transfer::send` → `transfer::submit`
* `accept::accept_transfer` → `accept::submit`
* `redeem::burn_and_withdraw` → `redeem::create_withdraw_account` + `redeem::submit_withdraw` (two-step)
* `consolidate::check_consolidate` → `consolidate::check_and_consolidate`
* All function signatures updated from positional args to struct params **Environment variables**
* `KEYCLOAK_URL` replaced with `KEYCLOAK_HOST` + `KEYCLOAK_REALM`
* `KEYCLOAK_CLIENT_SECRET` removed from password flow examples
* `LEDGER_PORT` removed; all curl examples now use `${LEDGER_HOST}` only **Infrastructure URLs**
* Attester URLs corrected: `attestor.bitsafe.dev` → `devnet.dlc.link/attestor-1`, `attestor.bitsafe.testnet` → `testnet.dlc.link/attestor-1`, `attestor.bitsafe.com` → `mainnet.dlc.link/attestor-1` **Daml templates**
* `CBTC.Issuance:DepositAccount` → `CBTC.DepositAccount:CBTCDepositAccount`
* Added `CBTC.WithdrawAccount:CBTCWithdrawAccount` to API Reference **SDK Setup additions**
* Added `cbtc::accept` and `cbtc::cancel_offers` to key modules table
* Added client credentials authentication example
* Added verification script, migration guide, and example.env file

### ✏️ Spelling correction: Attestor → Attester

Per reviewer feedback, corrected "Attestor" to "Attester" across all pages where it appeared in prose.

**Affected pages:** Quick Start, Minting and Burning, Security Deep Dive

### 🔒 Security Deep Dive: Attester network composition

Corrected the Attester network composition per reviewer input:

* **Before:** 9 pre-screened external node operators (including P2P and Everstake) + 1 BitSafe
* **After:** 3 external node operators (Finoa, Nethermind, DSRV) + 1 BitSafe-operated node (4 total)

### 📋 Integration Guides: Partner and feature updates

* Silvana listed as *(coming soon)* pending verification
* Hosted UI option updated from "coming soon" to *(coming soon)* per product team input

### 💰 Technical Reference: Fee confirmation

* Mint and burn fees confirmed at **0%** (changed from yellow warning callout to green confirmed callout)

***

## 2026-07-27

### 🔢 SDK and DAR version corrections

Version references had drifted out of sync with the released libraries, and three pages each stated a different `cbtc-lib` version. All version references now match the released tags.

**Corrected to actual released versions**

* `cbtc-lib` → **v0.6.4** (previously stated as v0.3.1 on API Reference, v0.4.2 on SDK Setup and Technical Reference, v0.3.0 on Quick Start)
* `canton-lib` crates `keycloak`, `ledger`, `registry`, `common` → **v0.6.1** (previously v0.3.1 / v0.5.0)
* Latest CBTC DAR → **`cbtc-1.2.1`**, shipped in `cbtc-lib` v0.6.4

**Affected pages:** SDK Setup and Installation, API Reference, Technical Reference

**Other fixes in this pass**

* API Reference install snippet corrected from `https://` to `ssh://` transport, matching SDK Setup — the HTTPS form does not work for this private repository
* DAR download links repointed from the `v0.3.1` and `v0.4.2` tags to `v0.6.4`
* Technical Reference repository table had `cbtc-lib` listed twice; the second row now correctly describes the CBTC DAR
* Clarified that the DAR version (`cbtc-1.2.1`) and the crate version (`v0.6.4`) are numbered independently, which was the likely source of the confusion
* Added a note that canton-lib crates must be pinned to the same tag `cbtc-lib` depends on, to avoid Cargo resolving two incompatible copies of the same types

**Removed the December 2025 restructure migration content**

## The "Migration Guide: December 2025 Restructure" section on SDK Setup, and the matching restructure note on the API Reference, described how the library used to be laid out. Both pages document how to use the current release, so the guidance now lives here in the changelog and in the [cleanup PR](https://github.com/DLC-link/cbtc-lib/pull/11) instead. The restructure moved module paths and function signatures only, with no runtime behaviour changes; code written before it needs its `use` statements updated to the module paths listed on SDK Setup.


# Trading Firms

Evaluate and onboard to CBTC as a trading firm. Find venue guides, reward playbooks, onboarding checklists, and everything you need to start trading institutional-grade Bitcoin on the Canton Network.


# Canton DeFi Ecosystem

The Canton Network ecosystem is growing rapidly with new wallets, DEXes, and DeFi applications launching regularly. This guide helps you navigate the available options for interacting with Canton Network and CBTC.

> Each venue and wallet maintains its own documentation and onboarding process. For introductions or access requests, contact <sales@bitsafe.finance>.

***

## Wallets

Store, send, receive, and manage your Canton assets.

| **Wallet**      | **Type**           | **Description**                                                                | **Website**                                   |
| --------------- | ------------------ | ------------------------------------------------------------------------------ | --------------------------------------------- |
| **Zoro**        | Self-custody       | SDK and API support for institutional traders                                  | [zorowallet.com](https://zorowallet.com/)     |
| **Console**     | Self-custody       | Browser wallet with clear signing and built-in risk checks                     | [consolewallet.io](https://consolewallet.io/) |
| **Loop**        | Self-custody       | Web-based, works in any browser, no extensions needed. Open source SDK.        | [cantonloop.com](https://cantonloop.com/)     |
| **Cantor8**     | Enterprise custody | Privacy-first mobile wallet. No registration, no data collection.              | [cantor8.tech](https://cantor8.tech/)         |
| **Bron**        | Self-custody       | Seedless recovery with MPC security, plus cross-chain swaps and staking        | [bron.org](https://bron.org/)                 |
| **Cansai**      | Self-custody       | First iOS-native Canton wallet with seamless Apple device sync                 | [cansai.app](https://cansai.app/)             |
| **Cypherock**   | Hardware           | Hardware wallet with decentralized key management                              | [cypherock.com](https://cypherock.com/)       |
| **Nightly**     | Multi-chain        | Multi-chain wallet with Canton support                                         | [nightly.app](https://nightly.app/)           |
| **Send Wallet** | Self-custody       | Passkey-first wallet. Log in with face or fingerprint instead of seed phrases. | [cantonwallet.com](https://cantonwallet.com/) |

***

## Trading Venues

Swap, trade, and provide liquidity on Canton.

| **Venue**          | **Type**     | **Available Pairs**         | **Website**                               |
| ------------------ | ------------ | --------------------------- | ----------------------------------------- |
| **Elk / Trngle**   | RFQ          | Multiple (custom available) | [trngle.xyz](https://trngle.xyz/)         |
| **Temple Digital** | CLOB         | CC-CBTC, USDCx-CBTC         | [temple.digital](https://temple.digital/) |
| **Tradefast**      | DEX / AMM    | BTC-CBTC, USDCx-CBTC        | [trade.fast](https://trade.fast/)         |
| **Bron**           | Wallet + DEX | BTC-CBTC, CC-CBTC           | [bron.org](https://bron.org/)             |
| **TradeCraft**     | AMM          | CC-CBTC                     | [tradecraft.fi](https://tradecraft.fi/)   |
| **Cantex**         | DEX          | Multiple pairs              | [cantex.io](https://cantex.io/)           |
| **Kairo**          | DEX          | Multiple pairs              | [kairo.ag](https://kairo.ag/)             |

***

## Lending Platforms

Borrow and lend on Canton.

| **Platform**               | **Status**  | **Description**                                                           | **Website**                                                       |
| -------------------------- | ----------- | ------------------------------------------------------------------------- | ----------------------------------------------------------------- |
| **Haven Digital Partners** | Live        | Institutional lending app on Canton                                       | [canton-lending.havendp.com](https://canton-lending.havendp.com/) |
| **Acme (Hello Moon)**      | Live        | Decentralized, overcollateralized lending pools / money markets on Canton | [acmemarkets.cc](https://acmemarkets.cc/)                         |
| **Verity (Hashrupt)**      | Live        | On-chain collateralized lending and loan lifecycle management on Canton   | [hashrupt.com](https://hashrupt.com/)                             |
| **Holdex**                 | In progress | Lending platform being built on Canton                                    | [holdex.io](https://holdex.io/)                                   |

***

## Other DeFi Apps

Asset management, prediction markets, and more on Canton.

| **App**      | **Category**      | **Website**                                 |
| ------------ | ----------------- | ------------------------------------------- |
| **Unhedged** | Prediction Market | [unhedged.gg](https://unhedged.gg/)         |
| **Modulo**   | DeFi Platform     | [modulo.finance](https://modulo.finance/)   |
| **AllDeFi**  | Asset Management  | [alldefi.finance](https://alldefi.finance/) |
| **Hecto**    | DeFi Platform     | [hecto.finance](https://hecto.finance/)     |

***

## Coming Soon

* **Additional Wallets:** Utila, Meteor Wallet

***

*This is a living document. The Canton Network ecosystem is evolving rapidly. Check back regularly for updates.*

***

> ℹ️ **Disclosures** This is not investment advice. Conduct independent due diligence before interacting with any third-party application.


# CBTC Ecosystem Docs

Programmatically use products on Canton that support CBTC. Find documentation and links for venues, wallets, and other apps in the ecosystem.

> ℹ️ Each venue and wallet maintains its own documentation and onboarding process. For introductions or access requests, contact <sales@bitsafe.finance>.

***

## Trading Venues

| **Venue**          | **Type**     | **Docs / Website**                                        |   |
| ------------------ | ------------ | --------------------------------------------------------- | - |
| **Elk / Trngle**   | RFQ          | [trngle.xyz](https://trngle.xyz/)                         |   |
| **Temple Digital** | CLOB         | [templedigitalgroup.com](https://templedigitalgroup.com/) |   |
| **Tradefast**      | DEX / AMM    | [trade.fast](https://trade.fast/)                         |   |
| **Bron**           | Wallet + DEX | [bron.org](https://bron.org/)                             |   |
| **TradeCraft**     | AMM          | [tradecraft.fi](https://tradecraft.fi/)                   |   |
| **Cantex**         | DEX          | [cantex.io](https://cantex.io/)                           |   |
| **Kairo**          | DEX          | [kairo.ag](https://kairo.ag/)                             |   |

***

## Wallets

| **Wallet**    | **Type**           | **Docs / Website**                            |
| ------------- | ------------------ | --------------------------------------------- |
| **Zoro**      | Self-custody       | [zorowallet.com](https://zorowallet.com/)     |
| **Console**   | Self-custody       | [consolewallet.io](https://consolewallet.io/) |
| **Loop**      | Self-custody       | [cantonloop.com](https://cantonloop.com/)     |
| **Cantor8**   | Enterprise custody | [cantor8.tech](https://cantor8.tech/)         |
| **Bron**      | Self-custody       | [bron.org](https://bron.org/)                 |
| **Cansai**    | Self-custody       | [cansai.app](https://cansai.app/)             |
| **Cypherock** | Hardware           | [cypherock.com](https://cypherock.com/)       |

***

> ℹ️ **Disclosures** Venue APIs and SDKs are maintained by their respective providers. BitSafe does not guarantee the availability, accuracy, or stability of third-party documentation. Conduct your own technical due diligence. This is not investment advice.


# FAQ for Trading Firms

Common questions from trading firms evaluating or onboarding to CBTC on Canton. This FAQ is compiled from sales conversations, partner calls, and Slack discussions.

***

## Fees and Costs

### What are the fees for minting and burning CBTC?

Minting and burning fees are **currently waived.** This is subject to change in the future. Check with the BitSafe BD team for the latest fee schedule.

### Are there trading fees on the venues?

Each venue sets its own fee structure:

* **Elk / Trngle:** Negotiable spreads based on volume
* **Temple Digital:** No platform fees currently
* **Tradefast:** Standard AMM swap fees
* **Bron:** Check venue documentation

***

## Anti-Gaming and Compliance

### What counts as "legitimate" trading activity?

Strategies must involve **real economic risk.** This includes market making, arbitrage, inventory rebalancing, directional trading, lending, and liquidity provision. Each of these generates genuine market activity and is eligible for rewards.

### What activity is flagged or prohibited?

Canton's tokenomics accountability process flags and shuts down **scripted back-and-forth transfers** (A to B to A) designed solely to farm rewards. If your strategy does not involve swapping into another asset, managing inventory risk, or providing liquidity, it will likely be flagged.

## Wallets and Infrastructure

### What wallet do I need?

You need a **Canton-compatible wallet** that supports CBTC. Recommended options for institutional traders include Zoro (self-custody with SDK/API), Console (browser-based), Loop (web-based, open source SDK), and Cantor8 (enterprise custody with multi-sig). See the Canton DeFi Ecosystem guide for full details.

### Do I need to run a Canton validator node?

Not necessarily. You can acquire CBTC via **OTC purchase** through Elk Capital or Trngle without running a node. However, if you want to **mint CBTC directly** from BTC, you will need a validator node. Multi-tenant validator options are available for firms that want node access without the full infrastructure build.

### Can I use multiple wallets?

Yes. You can use multiple Canton-compatible wallets for trading CBTC across different venues.

***

## Venues and Trading

### Which venue should I choose?

It depends on your trading style:

* **Need institutional-size execution with custom pairs?** Elk / Trngle RFQ
* **Want an order book with the best reward economics?** Temple Digital CLOB (40% bonus)
* **Want fast deployment with familiar DeFi infra?** Tradefast AMM
* **Want the simplest starting point?** Bron
* **Prefer hands-off yield?** Temple Digital LP or SciFeCap SMA See **Selecting a Trading Venue** for the full comparison and decision guide.

### What trading pairs are available?

The primary pairs are:

* **CBTC / USDXLR** - Canton-native yield-bearing stablecoin (primary pair, earns rewards from both assets)
* **CBTC / USDCx** - Cross-chain stablecoin
* **CBTC / CC** - Canton Coin Availability varies by venue. Check the venue comparison table in **Selecting a Trading Venue**.

### Who are the current market participants?

Active institutional counterparties on Canton include Elk Capital Markets, SciFeCap, HashKey Cloud, Desyn, IMC, QCP, and others. The trading firm pipeline is growing rapidly.

***

## Onboarding

### How long does onboarding take?

Typically **1 to 2 weeks** from initial signup to first trade, depending on your firm's readiness, compliance review timeline, and chosen venue's integration requirements.

### What is the onboarding process?

1. Complete the CBTC signup form
2. Sign MSA and complete KYC/AML
3. Set up a Canton wallet
4. Acquire CBTC (OTC or direct mint)
5. Connect to your chosen venue
6. Start trading See the **Onboarding Checklist** for the full step-by-step guide.

***

## Security

### How is CBTC secured?

CBTC uses **FROST threshold signatures** over Bitcoin UTXOs for decentralized custody. There is no single custodian. The Attestor Network collectively approves mints and burns using a threshold signing scheme. CBTC is fully 1:1 backed by BTC at all times.

### Has CBTC been audited?

Yes. CBTC has been audited by **Quantstamp.** The full audit report is available at [certificate.quantstamp.com](https://certificate.quantstamp.com/).

***

## Getting Started

> 📝 **Ready to start?**
>
> * [Complete the CBTC Signup Form](https://bitsafe.typeform.com/to/NsiwLKIY)
> * Email: <sales@bitsafe.finance>
> * Read the **Onboarding Checklist** for the full step-by-step process

***

> ℹ️ **Disclosures** Target yields are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Strategies carry risk; conduct independent due diligence. This is not investment advice.


# Getting Started: Venues, Wallets, and CBTC Acquisition

Canton supports multiple venue types for trading CBTC, each with different execution models, fee structures, and reward economics. This guide helps you choose the right venue for your firm.

***

> ### Choose Your Venue
>
> **Do you have in-house quant and dev resources?**
>
> * **Yes:** You're a fit for active trading. See the venue comparison below.
> * **No:** Consider **Temple Digital LP** (passive, single-sided) or **SciFeCap SMA** (fully managed, 8-10% target yield). **Do you need institutional-size execution with custom pairs?**
> * **Elk / Trngle RFQ.** Contact Elk Capital for spread negotiation based on expected volume. **Do you want an exchange-style order book with the best reward economics?**
> * **Temple Digital CLOB.** 40% bonus reward share on top of standard CBTC rewards. **Do you want fast deployment with familiar DeFi infrastructure?**
> * **Tradefast AMM.** Uniswap V2 style, fastest integration path. **Want the simplest starting point?**
> * **Bron.** Intuitive interface, comprehensive docs, quick onboarding.

***

## Active Trading Venues

For firms with in-house quant and dev resources running active strategies.

| **Venue**          | **Type**     | **Best For**                 | **Key Features**                                                          | **Pairs**                   |
| ------------------ | ------------ | ---------------------------- | ------------------------------------------------------------------------- | --------------------------- |
| **Elk / Trngle**   | RFQ          | Institutional-size execution | Programmatic OTC, negotiable spreads, custom pairs, bring your own wallet | Multiple (custom available) |
| **Temple Digital** | CLOB         | Order book traders           | Exchange-style order book, 40% bonus reward share, best reward economics  | CC-CBTC, USDCx-CBTC         |
| **Tradefast**      | AMM          | Fast deployment              | Uniswap V2 style, fastest integration path, familiar DeFi infrastructure  | BTC-CBTC, USDCx-CBTC        |
| **Bron**           | Wallet + DEX | Simple starting point        | Intuitive interface, comprehensive docs, quick onboarding                 | BTC-CBTC, CC-CBTC           |

***

## Passive Allocation Options

For firms seeking yield without active management or infrastructure build-out.

| **Option**            | **Type**            | **Description**                                 | **Key Details**                                                   |
| --------------------- | ------------------- | ----------------------------------------------- | ----------------------------------------------------------------- |
| **Temple Digital LP** | Liquidity Provision | Single-sided liquidity with no impermanent loss | Deposit CBTC, earn trading fees and Canton Coin rewards           |
| **SciFeCap SMA**      | Managed Account     | Fully managed strategy with 8-10% target yield  | No active management required. Professional portfolio management. |

> ℹ️ Target yields for passive options are illustrative only. Actual returns depend on market conditions, network activity, and token economics.

***

## Recommended Trading Pairs

| **Pair**          | **Description**                        | **Notes**                                     |
| ----------------- | -------------------------------------- | --------------------------------------------- |
| **CBTC / USDXLR** | Canton-native yield-bearing stablecoin | Primary pair. Earns rewards from both assets. |
| **CBTC / USDCx**  | Cross-chain stablecoin                 | Familiar stable pairing for BTC traders.      |
| **CBTC / CC**     | Canton Coin                            | Network token exposure.                       |

Pair availability varies by venue. Check the active trading venues table above for venue-specific pairs.

***

## Canton Wallet Options

You need a Canton-compatible wallet to hold and transact with CBTC.

| **Wallet**  | **Type**           | **Best For**                                       |
| ----------- | ------------------ | -------------------------------------------------- |
| **Zoro**    | Self-custody       | Firms wanting SDK/API access and full control      |
| **Console** | Self-custody       | Browser-based with clear signing and risk checks   |
| **Loop**    | Self-custody       | Web-based, no extensions needed, open source SDK   |
| **Cantor8** | Enterprise custody | Multi-signature security and regulatory compliance |

For the full list of wallets and DeFi apps, see the **Canton DeFi Ecosystem** page.

***

## Acquiring CBTC

Two paths depending on your infrastructure:

**Option A: OTC Purchase** *(fastest, no Canton node required)*

* Initiate a cross-chain CBTC swap with Trngle or an OTC purchase through Elk Capital
* Ideal for firms without a Canton validator node
* Contact Elk Capital for spread negotiation based on expected volume **Option B: Direct Minting** *(requires Canton validator node)*
* Call Rust APIs via cbtc-lib to mint CBTC directly from BTC
* More cost-effective for high-volume operations
* See the developer documentation at [docs.bitsafe.finance/product-suite/cbtc](https://docs.bitsafe.finance/product-suite/cbtc) for technical details

***

## Don't Have a Canton Validator Node?

> ℹ️ **Multi-tenant validators** provide a streamlined, cost-effective path to network participation without running a full Canton validator. BitSafe can connect you with trusted providers in the ecosystem.
>
> * Lower barrier to entry
> * Shared infrastructure costs
> * Get started in days, not weeks

***

## Next Steps

> 📝 **Ready to choose a venue?**
>
> * Review the **Prop Desk Playbook** for strategy recommendations
> * Follow the **Onboarding Checklist** to go from signup to first trade
> * [Complete the CBTC Signup Form](https://bitsafe.typeform.com/to/NsiwLKIY)
> * Email: <sales@bitsafe.finance>

***

> ℹ️ **Disclosures** Target yields are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Strategies carry risk; conduct independent due diligence. This is not investment advice.


# Glossary

Key terms and acronyms used across the institutional documentation. If you are coming from traditional finance or other blockchain networks, this page will help you navigate Canton-specific terminology.

***

## Assets and Tokens

**CBTC (Canton Bitcoin)**

Wrapped Bitcoin on the Canton Network. 1 CBTC is always backed 1:1 by BTC held in decentralized custody. CBTC is the primary asset for institutional trading on Canton.

**CC (Canton Coin)**

The native network rewards token on Canton. CC is earned through eligible transactions and distributed to participants. CC is not a stablecoin. Its value fluctuates based on market conditions.

**USDXLR**

A Canton-native yield-bearing stablecoin. The primary trading pair for CBTC. Trading CBTC/USDXLR earns rewards from both assets.

**USDCx**

A cross-chain stablecoin available on Canton. Provides a familiar stable pairing for BTC traders.

***

## Canton Network

**Canton Network**

An institutional-grade blockchain network designed for privacy, compliance, and atomic settlement. All participants are KYC-verified.

**Daml**

Canton's smart contract language. Used for building applications and defining transaction logic on the network.

**CIP-56**

Canton token standard. Defines how tokens (including CBTC) are created, transferred, and managed on Canton.

**Validator Node**

A node that participates in the Canton Network's consensus and transaction processing. Required for direct CBTC minting. Multi-tenant validator options are available for firms that do not want to run their own.

**Multi-Tenant Validator**

A shared validator node operated by a third-party provider. Allows firms to participate in the Canton Network without running their own infrastructure. Lower cost and faster setup than a dedicated node.

***

## Security and Custody

**FROST (Flexible Round-Optimized Schnorr Threshold)**

The threshold signature scheme used for CBTC's decentralized custody. FROST allows multiple parties to collectively sign Bitcoin transactions without any single party holding the full private key.

**Attestor Network**

The group of decentralized signers that collectively approve CBTC mints and burns using FROST threshold signatures. Currently operates on a 2-of-4 threshold.

**Threshold (M-of-N)**

The minimum number of attestors required to approve a transaction. For CBTC, 2 out of 4 attestors must sign to authorize a mint or burn.

**Proof of Reserve (PoR)**

Chainlink's verification mechanism confirming that all CBTC in circulation is fully backed 1:1 by BTC held in custody.

***

## Trading and Venues

**RFQ (Request for Quote)**

A trading model where a firm requests a price from a market maker and can accept or reject the quote. Used by Elk Capital / Trngle for institutional OTC execution.

**CLOB (Central Limit Order Book)**

A traditional exchange-style order book where buy and sell orders are matched by price and time priority. Used by Temple Digital.

**AMM (Automated Market Maker)**

A DeFi trading model where liquidity pools and mathematical formulas determine prices instead of an order book. Used by Tradefast.

**MEV (Miner/Maximal Extractable Value)**

The profit that can be extracted by reordering, inserting, or censoring transactions in a block. Canton eliminates MEV because it has no public mempool.

**Mempool**

A holding area for unconfirmed transactions visible to all network participants. Canton does not have a public mempool, which prevents front-running and sandwich attacks.

***

## Rewards and Economics

**Transaction-Count-Based Rewards**

Canton's reward model where every eligible transaction generates CC rewards regardless of transaction size. High-frequency strategies earn more rewards than low-frequency, high-volume strategies.

**Featured App (FA)**

A Canton application that has been designated as a Featured App, which affects reward multipliers for activity within that application.

**Anti-Gaming Policy**

Canton's tokenomics accountability process that detects and shuts down artificial transaction patterns (such as A to B to A transfers) designed to farm rewards without real economic activity.

***

## Agreements and Onboarding

**MSA (Master Service Agreement)**

The standard commercial agreement between a trading firm and BitSafe. Required before a firm can mint CBTC.

**KYC/AML (Know Your Customer / Anti-Money Laundering)**

Compliance checks required during onboarding. All Canton participants must be KYC-verified.

***

## Technical

**DAR (Daml Archive)**

A compiled Daml package file used to deploy smart contracts on Canton.

**cbtc-lib**

A Rust library for interacting with CBTC minting and burning functionality. Required for direct minting from BTC.

**Canton SDK**

The software development kit for building applications and submitting transactions on the Canton Network.


# Onboarding Checklist: From Signup to First Trade

This guide walks you through the complete onboarding process for trading CBTC on Canton, from initial signup to your first live trade. Expected timeline: 1 to 2 weeks depending on your firm's readiness and chosen venue.

***

## Step 1: Express Interest

> **Complete the CBTC Signup Form** [bitsafe.typeform.com/to/NsiwLKIY](https://bitsafe.typeform.com/to/NsiwLKIY) This registers your firm's interest and triggers outreach from the BitSafe BD team. You will be contacted to discuss your trading goals, preferred venues, and technical requirements.

***

## Step 2: Execute Agreements

> **Sign the MSA**
>
> * **Master Service Agreement (MSA):** Standard commercial terms for using BitSafe services
> * **KYC/AML:** Complete any required compliance checks Contact <sales@bitsafe.finance> if you have questions about the agreements.

***

## Step 3: Set Up a Canton Wallet

> **Choose and configure your wallet** You need a Canton-compatible wallet to hold and transact with CBTC. Options for institutional traders:

| **Wallet**                                                                                                                                                              | **Type**           | **Best For**                                       |
| ----------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------ | -------------------------------------------------- |
| **Zoro**                                                                                                                                                                | Self-custody       | Firms wanting SDK/API access and full control      |
| **Console**                                                                                                                                                             | Self-custody       | Browser-based with clear signing and risk checks   |
| **Loop**                                                                                                                                                                | Self-custody       | Web-based, no extensions needed, open source SDK   |
| **Cantor8**                                                                                                                                                             | Enterprise custody | Multi-signature security and regulatory compliance |
| For the full list of Canton wallets and SDK/API documentation, see the [Canton DeFi Ecosystem](https://docs.bitsafe.finance/trading-firms/canton-defi-ecosystem) guide. |                    |                                                    |

***

## Step 4: Acquire CBTC

> **Get CBTC into your wallet** Two paths depending on your infrastructure: **Option A: OTC Purchase** *(fastest, no Canton node required)*
>
> * Initiate a cross-chain CBTC swap with Trngle or an OTC purchase through Elk Capital
> * Ideal for firms without a Canton validator node
> * Contact Elk Capital for spread negotiation based on expected volume **Option B: Direct Minting** *(requires Canton validator node)*
> * Install the mint/burn software on your validator node
> * Call Rust APIs via cbtc-lib to mint CBTC directly from BTC
> * More cost-effective for high-volume operations
> * See the developer documentation at [docs.bitsafe.finance/product-suite/cbtc](https://docs.bitsafe.finance/product-suite/cbtc) for technical details

***

## Step 5: Choose and Connect to a Venue

> **Select your trading venue and integrate** See **Selecting a Trading Venue** for the full comparison. Quick summary:
>
> * **Elk / Trngle** (RFQ) - Institutional OTC, negotiable spreads, custom pairs
> * **Temple Digital** (CLOB) - Order book trading, 40% bonus reward share
> * **Tradefast** (AMM) - Uniswap V2 style, fastest integration
> * **Bron** - Intuitive interface, quick onboarding Each venue has its own API documentation and onboarding process. The BitSafe BD team will facilitate introductions.

***

## Step 6: Start Trading

> **You are live.**
>
> * Begin trading on your chosen venue
> * Every trade, swap, and lending transaction earns Canton Coin rewards
> * Rewards are transaction-count-based, not volume-based. High-frequency strategies earn more.
> * Review the **Prop Desk Playbook** for strategy recommendations **Recommended first trades:**
> * CBTC/USDXLR (primary pair, earns rewards from both assets)
> * CBTC/USDCx (familiar stable pairing)
> * CBTC/CC (Canton Coin exposure)

***

## Questions?

* **Email:** <sales@bitsafe.finance>
* **Common questions:** See the FAQ for Trading Firms
* **Technical questions:** See the developer documentation at [docs.bitsafe.finance/product-suite/cbtc](https://docs.bitsafe.finance/product-suite/cbtc)

***

> ℹ️ **Disclosures** Target yields are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Strategies carry risk; conduct independent due diligence. This is not investment advice.


# Overview

Trade CBTC on Canton with privacy, MEV protection, and decentralized custody on top of your trading P\&L.

***

## For Prop Trading Desks

> ⚡ Whether you're running market making, arbitrage, or inventory rebalancing strategies, Canton's transaction-count-based rewards mean your existing edge in execution speed and trade frequency translates directly into Canton Coin rewards on top of your P\&L.
>
> * **Prop Desk Playbook** - Strategies and reward mechanics
> * **Selecting a Trading Venue** - Compare RFQ, CLOB, and AMM options

***

> 💰
>
> #### Passive Yield
>
> Not running an active desk? SciFeCap SMA offers a fully managed option targeting 8-10% yield with no infrastructure required on your side. 🔍
>
> #### Evaluating CBTC?
>
> Start with **Why CBTC for Trading Firms** for Canton's differentiators, then check the **FAQ** for common questions from trading firms.

***

> 💡 **Trade BTC with privacy, MEV protection, and institutional infrastructure →** Start with the [Prop Desk Playbook](https://docs.bitsafe.finance/trading-firms/prop-desk-playbook) for strategies and reward mechanics, then use [Getting Started: Venues, Wallets, and CBTC Acquisition](https://docs.bitsafe.finance/trading-firms/getting-started-venues-wallets-and-cbtc-acquisition) to find the right fit for your desk.


# Prop Desk Playbook

This guide is for prop trading firms with in-house quant and dev resources running spot BTC strategies. It explains how Canton's reward model works, which strategies generate the most value, and what rules apply.

***

## How Canton's Reward Model Works for Active Traders

Canton Network rewards are based on **transaction count, not volume.** Every legitimate transaction involving CBTC generates Canton Coin (CC) rewards. For firms already running high-frequency spot strategies, this means your existing edge in execution speed and trade frequency translates directly into CC rewards on top of your trading P\&L.

* No minimum volume thresholds. Every accepted trade counts. Rewards are only generated on transactions accepted by the counterparty.
* Strategies you already run (market making, arbitrage, inventory rebalancing) generate both trading P\&L *and* network rewards.

***

## Strategies That Work

Canton's reward model rewards *frequency of legitimate economic activity.* These strategies naturally align with how prop firms already operate.

### Market Making

Quote CBTC/USDXLR or CBTC/USDCx with defined inventory bands. Earn spread P\&L plus Canton rewards on every fill.

### Cross-Venue Arbitrage

Exploit pricing differences between Elk RFQ, Temple CLOB, and Tradefast AMM. Each leg generates a separate reward-eligible transaction.

### Inventory Rebalancing

Rotate CBTC across venues and pairs as part of normal risk management. Every rebalance trade counts toward rewards.

### Directional Spot Trading

Apply existing spot BTC strategies to CBTC pairs. Same directional thesis, additional reward layer.

### Basis Trading

Trade CBTC vs BTC price differentials across Canton and external venues.

***

## Venue Selection for Prop Desks

Canton supports multiple venue types. The right choice depends on your trading style, technical stack, and preferred execution model.

### Which venue fits your desk?

**Do you need institutional-size execution with custom pairs?**

* **Elk / Trngle RFQ:** Programmatic OTC, negotiable spreads, bring your own wallet **Do you want an exchange-style order book with the best reward economics?**
* **Temple Digital CLOB:** 40% bonus reward share on top of standard CBTC rewards **Do you want fast deployment with familiar DeFi infrastructure?**
* **Tradefast AMM:** Uniswap V2 style, fastest integration path **Want the simplest starting point to test the waters?**
* **Bron:** Intuitive interface, comprehensive docs, quick onboarding For full venue comparison tables and integration details, see **Selecting a Trading Venue**.

***

## Anti-Gaming Rules

> ⚠️ **Important:** Strategies must involve real economic risk. Canton's tokenomics accountability process flags and shuts down scripted back-and-forth transfers (A to B to A) designed solely to farm rewards. If your strategy does not involve swapping into another asset, managing inventory risk, or providing liquidity, it will likely be flagged. Legitimate activity includes: market making, arbitrage, inventory rebalancing, directional trading, lending, and liquidity provision.

***

## Getting Started

> 📝 **Ready to start?**
>
> 1. Compare venues in **Selecting a Trading Venue**
>
> 2. Follow the **Onboarding Checklist** from signup to first trade
>
> * [Complete the CBTC Signup Form](https://bitsafe.typeform.com/to/NsiwLKIY)
> * Email: <sales@bitsafe.finance>

***

> ℹ️ **Disclosures** Target yields are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Strategies carry risk; conduct independent due diligence. This is not investment advice.


# Resources

Consolidated links, documentation, and contact information for trading firms working with CBTC on Canton.

***

## Get Started

| **Resource**         | **Link**                                                                     |
| -------------------- | ---------------------------------------------------------------------------- |
| CBTC Signup Form     | [bitsafe.typeform.com/to/NsiwLKIY](https://bitsafe.typeform.com/to/NsiwLKIY) |
| Sales and BD Contact | <sales@bitsafe.finance>                                                      |

***

## Technical Documentation

| **Document**                            | **Link**                                                                                                                               |
| --------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------- |
| CBTC Developer Documentation            | [docs.bitsafe.finance/product-suite/cbtc](https://docs.bitsafe.finance/product-suite/cbtc)                                             |
| FROST Whitepaper (threshold signatures) | [eprint.iacr.org/2020/852](https://eprint.iacr.org/2020/852)                                                                           |
| Canton Network Whitepaper               | [canton.network/whitepapers](https://canton.network/whitepapers)                                                                       |
| Quantstamp Audit Report                 | [certificate.quantstamp.com](https://certificate.quantstamp.com/)                                                                      |
| CBTC Technical Documentation (legacy)   | [docs.bitsafe.finance/bitsafe-documentation/product-suite/cbtc](https://docs.bitsafe.finance/bitsafe-documentation/product-suite/cbtc) |
| FROST Security Deep Dive                | [docs.bitsafe.finance/.../a-deep-dive-into-frost](https://docs.bitsafe.finance/.../a-deep-dive-into-frost)                             |

***

## Venue Links

| **Venue**      | **Type**     | **Website**                               |
| -------------- | ------------ | ----------------------------------------- |
| Elk / Trngle   | RFQ          | [trngle.xyz](https://trngle.xyz/)         |
| Temple Digital | CLOB         | [temple.digital](https://temple.digital/) |
| Tradefast      | AMM          | [trade.fast](https://trade.fast/)         |
| Bron           | Wallet + DEX | [bron.org](https://bron.org/)             |
| TradeCraft     | AMM          | [tradecraft.fi](https://tradecraft.fi/)   |

***

## Wallet Links

| **Wallet** | **Website**                                   |
| ---------- | --------------------------------------------- |
| Zoro       | [zorowallet.com](https://zorowallet.com/)     |
| Console    | [consolewallet.io](https://consolewallet.io/) |
| Loop       | [cantonloop.com](https://cantonloop.com/)     |
| Cantor8    | [cantor8.tech](https://cantor8.tech/)         |
| Bron       | [bron.org](https://bron.org/)                 |
| Cansai     | [cansai.app](https://cansai.app/)             |
| Cypherock  | [cypherock.com](https://cypherock.com/)       |

***

## Trading Documentation

All institutional docs live at [docs.bitsafe.finance/trading-firms](https://docs.bitsafe.finance/trading-firms).

* **Why CBTC for Trading Firms:** Canton's differentiators, security model, and use cases
* **Prop Desk Playbook:** Strategies, reward mechanics, and anti-gaming rules
* **Selecting a Trading Venue:** Venue comparison, decision guide, and wallet options
* **Canton DeFi Ecosystem:** Full wallet, DEX, and DeFi app directory
* **Onboarding Checklist:** Step-by-step from signup to first trade
* **FAQ for Trading Firms:** Common questions answered Developer documentation lives at [docs.bitsafe.finance/product-suite/cbtc](https://docs.bitsafe.finance/product-suite/cbtc).

***

## Standardized Disclosures

> ℹ️ **Risk Disclosure** Target yields and reward projections are illustrative only and are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Trading strategies carry risk. Conduct independent due diligence before making any trading or allocation decisions. ℹ️ **Not Investment Advice** Nothing in this documentation constitutes investment, legal, or tax advice. All information is provided for informational purposes only.


# Why CBTC for Trading Firms

CBTC is the native wrapped Bitcoin on the Canton Network, designed for institutional trading with privacy, MEV protection, and decentralized custody. This page explains why trading firms are integrating CBTC into their operations.

***

## Canton's Differentiators for Traders

| **🛡️ MEV Protection**                                   | **🔒 Private Positions**                                           | **🏛️ Institutional Counterparties**                                      |
| -------------------------------------------------------- | ------------------------------------------------------------------ | ------------------------------------------------------------------------- |
| No public mempool. No front-running or sandwich attacks. | Your positions and strategy are not visible to other participants. | All nodes are KYC-verified. Trade against vetted, compliant institutions. |

***

## How CBTC Is Secured

CBTC uses **FROST threshold signatures** over Bitcoin UTXOs for decentralized custody. There is no single custodian holding the underlying BTC.

* **1:1 BTC backing** at all times, verified by Chainlink Proof of Reserve
* **Decentralized Attestor Network** collectively approves mints and burns using a 2-of-4 threshold signing scheme
* **No single point of failure.** No individual entity can unilaterally move the underlying Bitcoin
* **Audited by Quantstamp.** Full report available at [certificate.quantstamp.com](https://certificate.quantstamp.com/)

***

## How to Trade CBTC

> #### Active Trading
>
> For firms with in-house quant and dev resources running spot BTC strategies.
>
> * Market making, arbitrage, inventory rebalancing, directional trading
> * Multiple venue types: RFQ, CLOB, AMM
> * Transaction-count-based rewards favor high-frequency strategies See the **Prop Desk Playbook** for strategy details.

***

## Use Cases

> 📈 **Spot and Perpetual Trading** Trade across RFQ (Elk/Trngle), CLOB (Temple Digital), and AMM (Tradefast) venues. No platform fees on most venues currently. 📊 **Lending and Borrowing** Lend CBTC on Haven Digital, Acme Markets, or Verity. Earn yield from interest on every lending transaction. Over-collateralized and smart contract secured. 💎 **Collateral Management** Use CBTC as high-quality collateral across multiple Canton venues. Atomic settlement reduces counterparty risk and improves capital efficiency. 🏗️ **Structured Products** Combine derivatives, lending, and spot markets to build risk-managed structured products. Canton's privacy model keeps your strategies confidential.

***

## Recommended Trading Pairs

| **Pair**          | **Description**                        | **Notes**                                         |
| ----------------- | -------------------------------------- | ------------------------------------------------- |
| **CBTC / USDXLR** | Canton-native yield-bearing stablecoin | Primary pair. Earns rewards from both assets.     |
| **CBTC / USDCx**  | Cross-chain stablecoin                 | Familiar stable pairing for BTC traders.          |
| **CBTC / CC**     | Canton Coin                            | Network token exposure. Available on most venues. |

Pair availability varies by venue. See **Selecting a Trading Venue** for venue-specific details.

***

## Technical Resources

* [CBTC Technical Documentation](https://docs.bitsafe.finance/product-suite/cbtc)
* [FROST Whitepaper](https://eprint.iacr.org/2020/852) (threshold signature security model)
* [Canton Network Whitepaper](https://www.canton.network/whitepapers)
* [Quantstamp Audit Report](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html)

***

## Next Steps

> 📝 **Ready to get started?**
>
> * Read the **Prop Desk Playbook** to understand strategies and reward mechanics
> * Compare venues in **Selecting a Trading Venue**
> * Follow the **Onboarding Checklist** to go from signup to first trade
> * [Complete the CBTC Signup Form](https://bitsafe.typeform.com/to/NsiwLKIY)
> * Email: <sales@bitsafe.finance>

***

> ℹ️ **Disclosures** Target yields are not guaranteed. Canton Coin rewards depend on network activity, token economics, and market conditions. Strategies carry risk; conduct independent due diligence. This is not investment advice.


# Developers

Build integrations, wallets, and DeFi protocols with CBTC on the Canton Network. This section covers everything you need to go from first API call to production deployment.

## Getting Started

* [CBTC Overview](/developers/cbtc-overview) - Architecture and core concepts
* [SDK Setup and Installation](/developers/sdk-setup-and-installation) - Install cbtc-lib, upload the DAR files, and configure your environment. **Start here.**
* [CBTC Quick Start](/developers/cbtc-quick-start) - Mint your first CBTC in 15 minutes
* [CBTC Testnet Guide](/developers/cbtc-testnet-guide) - Test on Canton testnet before going live

## Core Operations

* [CBTC Minting and Burning](/developers/cbtc-minting-and-burning) - Convert BTC to CBTC and back with code
* [CBTC Authentication](/developers/cbtc-authentication) - Authenticate with the Canton Ledger API
* [CBTC API Reference](/developers/cbtc-api-reference) - Full API endpoint documentation
* [Instrument ID Management](/developers/instrument-id-management) - Manage CBTC instrument identifiers

## Advanced

* [Integration Guides](/developers/integration-guides) - Integrate CBTC into your platform
* [Technical Reference](/developers/technical-reference) - Detailed technical specifications
* [Security Deep Dive](/developers/security-deep-dive) - Threat model, FROST signatures, and audit results

## Reference

* [Resources](/developers/resources) - Audit reports, whitepapers, and external links
* [Changelog](/developers/changelog) - Release notes and version history


# CBTC API Reference

> ⚠️ **API Stability Notice:** All endpoints and interfaces are subject to change without notice. There is no formal versioning policy today. Breaking changes are communicated via the site changelog.

***

## CBTC SDK Reference: cbtc-lib (Rust)

For most integrations, we recommend using **cbtc-lib** (Rust) rather than raw API calls:

* **Repository:** [github.com/DLC-link/cbtc-lib](https://github.com/DLC-link/cbtc-lib)
* **Current version:** v0.6.4
* **Crate name:** `cbtc` (add via `cbtc = { git = "ssh://git@github.com/DLC-link/cbtc-lib.git", tag = "v0.6.4" }`)
* **Lower-level library:** [github.com/DLC-link/canton-lib](https://github.com/DLC-link/canton-lib) (v0.6.1)
* **Code examples:** [github.com/DLC-link/cbtc-lib/tree/main/examples](https://github.com/DLC-link/cbtc-lib/tree/main/examples)
* **Setup guide:** [SDK Setup and Installation](https://docs.bitsafe.finance/developers/sdk-setup-and-installation)

***

## Overview: Canton Ledger API for CBTC Operations

All CBTC operations (minting, burning, transferring wrapped Bitcoin) are performed through the **Canton Ledger API** (also called the JSON Ledger API). There is no separate "CBTC API." You interact with CBTC by exercising choices on Daml smart contracts running on your Canton participant node.

**Base URL:** `https://<your-participant-host>/v2/`

**Authentication:** Bearer token (JWT) from your OIDC provider. See the [Authentication Guide](https://docs.bitsafe.finance/developers/cbtc-authentication).

**Content-Type:** `application/json` for all requests.

***

## Prerequisites

Before calling any CBTC API:

1. **Canton participant node** running and connected to the network
2. **CBTC DAR files** installed on your participant - [download from GitHub](https://github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars)
3. **Valid JWT** from your OIDC provider (Keycloak officially supported)
4. **Party ID** allocated on your participant

***

## Canton Ledger API Endpoints

For full endpoint documentation covering the Canton Ledger API (including all endpoints used by CBTC operations), refer to the official Canton documentation:

[**Canton JSON Ledger API Documentation →**](https://docs.digitalasset.com/build/3.4/explanations/json-api/index.html)

***

## CBTC Instrument ID Management: Devnet, Testnet, and Mainnet

CBTC uses the Canton Token Standard. To interact with CBTC programmatically, you need the correct **Instrument ID** for your target network.

> ⚠️ **Instrument IDs differ across networks** (devnet, testnet, mainnet). Always fetch the latest from the metadata URL rather than hardcoding.

### Devnet

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-dev.com"
}
```

**Metadata:** [View](https://api.utilities.digitalasset-dev.com/api/token-standard/v0/registrars/cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff/registry/metadata/v1/instruments)

### Testnet

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-staging.com"
}
```

**Metadata:** [View](https://api.utilities.digitalasset-staging.com/api/token-standard/v0/registrars/cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f/registry/metadata/v1/instruments)

### Mainnet

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12205af3b949a04776fc48cdcc05a060f6bda2e470632935f375d1049a8546a3b262",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset.com"
}
```

**Metadata:** [View](https://api.utilities.digitalasset.com/api/token-standard/v0/registrars/cbtc-network::12205af3b949a04776fc48cdcc05a060f6bda2e470632935f375d1049a8546a3b262/registry/metadata/v1/instruments)

**Token Standard API Reference:** [Canton Token Standard Docs](https://docs.dev.sync.global/app_dev/token_standard/index.html#api-references)

> 💡 **Polling pattern:** Instrument IDs can change due to network dynamics (e.g., DAR upgrades). Query the metadata URL periodically rather than hardcoding values. There is currently no push notification for ID changes - this is a known gap.

***

## Rate Limits

There are no BitSafe-imposed rate limits on the Canton Ledger API. However:

* **Canton network throughput:** Transfers take a few seconds each. Approximately 500 transfers per 10-minute period is near the current practical limit.
* **Your participant node:** Performance depends on your infrastructure. Monitor node resource usage under load.

***

## API Error Handling for CBTC Operations

| Error               | Cause                               | Resolution                              |
| ------------------- | ----------------------------------- | --------------------------------------- |
| `401 Unauthorized`  | Invalid or expired JWT              | Re-authenticate with your OIDC provider |
| `404 Not Found`     | Contract ID no longer active        | Re-query for current contract IDs       |
| `409 Conflict`      | Duplicate command ID                | Use a unique `commandId` per request    |
| UTXO limit exceeded | Too many UTXOs for a party (max 10) | Consolidate UTXOs using cbtc-lib        |

***


# CBTC Authentication

> ⚠️ **API Disclaimer:** CBTC APIs are subject to change. Authentication flows may evolve as Canton's identity layer matures.

***

## Overview: How Authentication Works for CBTC on Canton

All CBTC operations go through the Canton Ledger API, which requires a valid **JWT (JSON Web Token)** for every request. The JWT is issued by an **OIDC (OpenID Connect) provider** connected to your Canton participant node.

This guide covers two authentication options for developers building with CBTC and the Canton Network:

* **Keycloak** (officially supported by BitSafe)
* **Auth0** (community example, not officially maintained) For deeper background on how Canton handles authentication and authorization at the platform level, see the [Canton Authorization Documentation](https://docs.digitalasset.com/build/3.4/sdlc-howtos/applications/secure/authorization.html).

***

## CBTC Authentication Flow: JWT and OIDC

```mermaid
sequenceDiagram
 participant App as Your Application
 participant OIDC as OIDC Provider<br>(Keycloak / Auth0)
 participant Canton as Canton Participant<br>(Ledger API)

 App->>OIDC: 1. Request token (client credentials or auth code)
 OIDC-->>App: 2. JWT access token
 App->>Canton: 3. API call with Bearer token
 Canton-->>App: 4. Response
```

***

## Set Up Keycloak for CBTC Authentication (Officially Supported) ✅

Keycloak is the **officially supported** OIDC provider for CBTC integrations. BitSafe engineering provides support for Keycloak-based authentication.

### Prerequisites

* Keycloak instance running and accessible
* A realm configured for your Canton participant
* A client application registered in Keycloak

### Step 1: Register a Client

In your Keycloak admin console:

1. Navigate to your realm → **Clients** → **Create client**
2. Set **Client type** to `OpenID Connect`
3. Set **Client ID** (e.g., `cbtc-minting-app`)
4. Enable **Client authentication** (for server-to-server flows)
5. Under **Service account roles**, enable as needed

### Step 2: Configure Your Canton Participant

Your Canton participant must be configured to trust your OIDC provider. Participant configuration is complex and environment-specific. Refer to the official validator operator documentation:

[**Canton Validator Operator Guide →**](https://docs.dev.sync.global/validator_operator/index.html)

### Step 3: Obtain a Token

**Client Credentials flow** (for server-to-server / backend integrations):

```bash
curl -X POST "https://<your-keycloak>/auth/realms/<your-realm>/protocol/openid-connect/token" \
 -H "Content-Type: application/x-www-form-urlencoded" \
 -d "grant_type=client_credentials" \
 -d "client_id=cbtc-minting-app" \
 -d "client_secret=$CLIENT_SECRET"
```

**Password grant flow** (for user-facing / interactive applications):

```bash
curl -X POST "https://<your-keycloak>/auth/realms/<your-realm>/protocol/openid-connect/token" \
 -H "Content-Type: application/x-www-form-urlencoded" \
 -d "grant_type=password" \
 -d "client_id=cbtc-minting-app" \
 -d "username=$KEYCLOAK_USERNAME" \
 -d "password=$KEYCLOAK_PASSWORD"
```

**Response** (both flows):

```json
{
 "access_token": "eyJhbGciOiJSUzI1NiIs...",
 "expires_in": 300,
 "token_type": "Bearer"
}
```

### Step 4: Use the Token

Include the token in all Canton Ledger API calls:

```bash
curl -X POST "https://<your-participant>/v2/state/active-contracts" \
 -H "Authorization: Bearer $ACCESS_TOKEN" \
 -H "Content-Type: application/json" \
 -d '{... }'
```

### Token Refresh

Tokens expire (typically 5 minutes for Keycloak). Your application should:

1. Cache the token until near expiry
2. Request a new token before the current one expires
3. Retry failed requests with a fresh token if you receive a `401`

***

## Set Up Auth0 for CBTC Authentication (Community Example) ⚠️

> 💡 **Auth0 compatibility.** Both Keycloak and Auth0 follow the OAuth2/OIDC standard, so the login flow and token usage are identical. There is one known caveat: Auth0 requires an extra `audience` parameter in the token request. The `cbtc-lib` and `canton-lib` libraries **do not pass this parameter by default**, so they won't work out of the box with Auth0. This is a straightforward fix on either the library side or the client side. See the workaround below. BitSafe engineering support covers **Keycloak-based authentication only**. For Auth0-specific configuration issues, refer to [Auth0's documentation](https://auth0.com/docs).

### Prerequisites

* Auth0 tenant and API configured
* Application registered as **Machine to Machine** (for backend) or **Single Page Application** (for frontend)

### Step 1: Create an Auth0 API

In the Auth0 dashboard:

1. Navigate to **Applications** → **APIs** → **Create API**
2. Set **Name** (e.g., `Canton Ledger API`)
3. Set **Identifier** to your participant's Ledger API URL
4. Set **Signing Algorithm** to `RS256`

### Step 2: Register a Machine-to-Machine Application

1. Navigate to **Applications** → **Create Application**
2. Select **Machine to Machine Applications**
3. Authorise the application to call your Canton Ledger API
4. Note the **Client ID** and **Client Secret**

### Step 3: Configure Your Canton Participant

Point your participant to Auth0's JWKS endpoint. Participant configuration is complex and environment-specific. Refer to the official validator operator documentation:

[**Canton Validator Operator Guide →**](https://docs.dev.sync.global/validator_operator/index.html)

### Step 4: Obtain a Token

```bash
curl -X POST "https://<your-auth0-domain>/oauth/token" \
 -H "Content-Type: application/json" \
 -d '{
 "client_id": "'$CLIENT_ID'",
 "client_secret": "'$CLIENT_SECRET'",
 "audience": "https://<your-participant>/v2/",
 "grant_type": "client_credentials"
 }'
```

> ⚠️ **The `audience` parameter is required for Auth0.** This is the key difference from Keycloak. Without it, Auth0 will return an opaque token that the Canton participant will reject. Set `audience` to your participant's Ledger API base URL. **If using cbtc-lib / canton-lib:** The Rust libraries' `keycloak::login::password` and `keycloak::login::client_credentials` functions do not pass an `audience` parameter. To use Auth0, you'll need to either:
>
> 1. Make the token request directly via HTTP (as shown above) instead of using the library helper
> 2. Patch the login functions to include the `audience` field, which is a small change A library-level fix may be shipped in a future release of `canton-lib`.

### Step 5: Use the Token

Same as Keycloak. Include the Bearer token in all API requests.

***

## Wallet-Based Authentication for Canton dApps

For applications that use Canton-compatible wallets (Loop, Console/Zoro, Bron), authentication is handled by the wallet provider. Your application receives a JWT through the wallet's SDK or connect flow.

Supported wallets:

* **Loop Wallet**
* **Console / Zoro Wallet**
* **Bron Wallet**
* **WalletConnect** (for dApp integrations)
* **Node login** (direct participant authentication) See the [Integration Guides](https://docs.bitsafe.finance/developers/integration-guides) for wallet-specific connection patterns.

***

## Troubleshooting

| Issue                               | Cause                                            | Resolution                                                                |
| ----------------------------------- | ------------------------------------------------ | ------------------------------------------------------------------------- |
| `401 Unauthorized` on every request | JWT not trusted by participant                   | Verify JWKS URL in participant config matches your OIDC provider          |
| Token expires immediately           | Clock skew between OIDC provider and participant | Sync system clocks (NTP)                                                  |
| CORS errors in browser              | Ingress not configured for CORS                  | Add CORS annotations to your ingress - see Minting App Installation Guide |
| `invalid_grant` from OIDC provider  | Client secret rotated or incorrect               | Regenerate and update client secret                                       |

***

## JWT Security Best Practices for Canton Applications

* **Never expose client secrets** in frontend code. Use the Client Credentials flow only from backend services.
* **Rotate secrets regularly.** Update client secrets in both your OIDC provider and your application config.
* **Use short-lived tokens.** The default 5-minute expiry is appropriate for most use cases.
* **Restrict party access.** Configure your JWT claims to limit which Canton parties a token can act as.

***


# CBTC Minting and Burning

> ⚠️ **API Disclaimer:** CBTC APIs are subject to change. There is no formal versioning policy today. Breaking changes are communicated via the site changelog.

***

## Overview: The Full BTC to CBTC Lifecycle

This guide covers the complete lifecycle of converting Bitcoin to CBTC and back: minting (BTC to CBTC on Canton) and burning (CBTC back to BTC). For a quick end-to-end walkthrough, see the [CBTC Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start). This guide goes deeper into each step, covering edge cases, error handling, and recovery patterns for production integrations.

> 🛠️ **Prerequisite: install the SDK.** The Rust examples on this page use the `cbtc-lib` SDK. See [SDK Setup and Installation](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) for installing `cbtc-lib` and `canton-lib`, uploading the CBTC DAR files, and configuring your environment.

**Key facts:**

* **Exchange rate:** 1 BTC = 1 CBTC, always
* **Confirmations required:** 6 Bitcoin block confirmations (\~60 minutes)
* **Processing time:** Additional 60-120 seconds after confirmations for Attestor verification
* **Wallet requirement:** Taproot-compatible Bitcoin wallet (P2TR addresses)
* **Transaction limits:** 0.0001 BTC minimum, 5 BTC maximum by default - set per account and adjustable on request (see below)
* **Minter credential:** Required before you can create a deposit or withdraw account (see below)

***

## Transaction Limits

Mint and burn amounts are bounded by **per-account limits**. The defaults are:

| Limit       | Default    |
| ----------- | ---------- |
| **Minimum** | 0.0001 BTC |
| **Maximum** | 5 BTC      |

> 💡 **Limits are adjustable.** These are defaults, not fixed protocol constraints. If your integration needs a different range, contact <sales@bitsafe.finance> to have your account limits modified.

### Read limits from the account, do not hardcode them

Because limits are set per account and can be changed on request, **read them at runtime rather than hardcoding the defaults**. They are carried on the Deposit Account (for minting) and the Withdraw Account (for burning), and are returned by the deposit account status call:

```rust
use cbtc::mint_redeem::mint;

let status = mint::get_deposit_account_status(mint::GetDepositAccountStatusParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
 api_url: api_url.clone(),
 account_contract_id: deposit_account.contract_id.clone(),
}).await?;

if let Some(limits) = &status.limits {
 println!("Min: {:?} | Max: {:?}", limits.min_amount, limits.max_amount);
}
```

Both fields are optional. `None` means that bound is not enforced for the account:

```rust
pub struct Limits {
 pub min_amount: Option<DamlDecimal>, // serialised as "minAmount"
 pub max_amount: Option<DamlDecimal>, // serialised as "maxAmount"
}
```

### Validate before submitting

`cbtc::mint_redeem::models::check_limits` validates an amount against a set of limits locally, so an out-of-range request fails in your code instead of being rejected downstream:

```rust
use cbtc::mint_redeem::models::check_limits;

check_limits("Withdraw", amount.clone(), &withdraw_account.limits)?;
```

It returns a descriptive error - `"Withdraw amount 0.00001 is below minimum 0.0001"` or `"... exceeds maximum 5"` - and succeeds when no limits are set.

***

## Prerequisite: Obtain a Minter Credential

> ⚠️ **Minting and burning require a Minter credential.** This is a hard requirement, not an optional step. Creating a deposit account or a withdraw account will fail without one. Transferring, receiving, and holding CBTC do **not** require a credential — only minting and burning do.

A Minter credential is a Daml contract issued to your Canton party by the **CBTC registrar**. It carries a claim with the property `hasCBTCRole` and the value `Minter`, and you pass its contract ID into the account-creation calls.

### How to request one

Minter credentials are issued as part of commercial onboarding. To request one, contact the BitSafe team at <sales@bitsafe.finance> with your Canton Party ID and target environment (testnet or mainnet).

### Check whether you already hold one

Once the registrar has issued your credential, use the `cbtc::credentials` module to find it. A credential is a Minter credential if any of its claims has `property == "hasCBTCRole"` and `value == "Minter"`:

```rust
use cbtc::credentials::{list_credentials, ListCredentialsParams};

let credentials = list_credentials(ListCredentialsParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
}).await?;

let minter_credential_cids: Vec<String> = credentials
 .iter()
 .filter(|c| {
 c.claims
 .iter()
 .any(|claim| claim.property == "hasCBTCRole" && claim.value == "Minter")
 })
 .map(|c| c.contract_id.clone())
 .collect();

if minter_credential_cids.is_empty() {
 return Err("No Minter credential found for this party".into());
}
```

### Accept a pending credential offer

The registrar issues the credential as an **offer** that your party must accept before it becomes active. If `list_credentials` returns nothing, check for a pending offer and accept it:

```rust
use cbtc::credentials::{
 accept_credential_offer, find_user_service, list_credential_offers,
 AcceptCredentialOfferParams, FindUserServiceParams, ListCredentialOffersParams,
};

let user_service = find_user_service(FindUserServiceParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
}).await?;

let offers = list_credential_offers(ListCredentialOffersParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
}).await?;

accept_credential_offer(AcceptCredentialOfferParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
 user_service_contract_id: user_service.contract_id.clone(),
 user_service_template_id: user_service.template_id.clone(),
 credential_offer_cid: offers[0].contract_id.clone(),
}).await?;
```

> ℹ️ **Accepting a credential is permanent.** It creates a persistent on-ledger contract with no archive choice, so a credential cannot be un-accepted. Accept only the offer you actually intend to use.

A complete runnable version of this flow is in the library's [`credentials` example](https://github.com/DLC-link/cbtc-lib/blob/v0.6.4/examples/credentials.rs).

***

## How to Mint CBTC: Deposit Bitcoin and Receive Wrapped BTC on Canton

### How It Works

```mermaid
sequenceDiagram
 participant Dev as Your App
 participant Canton as Canton Ledger API
 participant BTC as Bitcoin Network
 participant Att as Attestor Network

 Dev->>Canton: 1. Authenticate (get JWT)
 Dev->>Canton: 2. Create Deposit Account
 Canton-->>Dev: Deposit Account ID
 Dev->>Canton: 3. Request BTC Deposit Address
 Canton-->>Dev: Taproot address (P2TR)
 Dev->>BTC: 4. Send BTC to address
 BTC-->>Att: 5. Attestors monitor for 6 confirmations
 Att->>Canton: 6. Submit ConfirmDepositAction (threshold)
 Canton-->>Dev: 7. CBTC minted to your party
```

### Step-by-Step

Step 1: Authenticate

Obtain a JWT token from your OIDC provider (Keycloak is officially supported). See the [Authentication Guide](https://docs.bitsafe.finance/developers/cbtc-authentication) for setup details.

Step 2: Create a Deposit Account

A Deposit Account is required before you can generate deposit addresses. This call requires the Minter credential contract IDs obtained in the prerequisite step above.

**Using cbtc-lib (Rust):**

```rust
use cbtc::mint_redeem::{mint, attestor};

// First get account rules from the Attestor
let account_rules = attestor::get_account_contract_rules(&api_url).await?;

let deposit_account = mint::create_deposit_account(mint::CreateDepositAccountParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 account_rules,
 credential_cids: minter_credential_cids.clone(),
}).await?;

println!("Deposit Account ID: {}", deposit_account.contract_id);
```

**Using Canton API (curl):**

You can fetch the CBTCDepositAccountRules from the BitSafe API's `/cbtc/v1/account-contract-rules` endpoint

> ⚠️ **A Minter credential is required.** The `CreateDepositAccount` choice takes your Minter credential contract IDs as an argument. See [Prerequisite: Obtain a Minter Credential](#prerequisite-obtain-a-minter-credential) above. Requests without a valid credential are rejected.

```bash
curl -X POST '${LEDGER_HOST}/v2/commands/submit-and-wait-for-transaction-tree' \
 --header 'Authorization: Bearer ${ACCESS_TOKEN}' \
 --data '{
 "commands": [
 {
 "ExerciseCommand": {
 "templateId": "#cbtc:CBTC.DepositAccount:CBTCDepositAccountRules",
 "contractId": "${DA_RULES_CID}",
 "choice": "CBTCDepositAccountRules_CreateDepositAccount",
 "choiceArgument": {
 "owner" : "${OWNER_PARTY}"
 }
 }
 }
 ],
 "actAs": [
 "${OWNER_PARTY}"
 ],
 "commandId": "someCommandID",
 "disclosedContracts": [
 {
 "templateId": "#cbtc:CBTC.DepositAccount:CBTCDepositAccountRules",
 "contractId": "${DA_RULES_CID}",
 "createdEventBlob": "${DA_RULES_BLOB}",
 "synchronizerId": ""
 }
 ]
}'
```

{% hint style="info" %}
Note: The submit-and-wait-for-transaction-tree endpoint is deprecated in Canton 3.5 but remains functional on 3.5.1. Consider migrating to submit-and-wait-for-transaction for new integrations.
{% endhint %}

Step 3: Generate a Bitcoin Deposit Address

Each deposit address is unique to your account and is a standard **Taproot (P2TR)** address.

**Using cbtc-lib (Rust):**

```rust
use cbtc::mint_redeem::mint;

let btc_address = mint::get_bitcoin_address(mint::GetBitcoinAddressParams {
 api_url: api_url.clone(),
 account_id: deposit_account.contract_id.clone(),
}).await?;

println!("Send BTC to: {}", btc_address);
```

Step 4: Send Bitcoin

Send the exact amount of BTC you want to mint as CBTC to the generated Taproot address from your Bitcoin wallet.

Step 5: Wait for Confirmations

The Attestor network automatically monitors the Bitcoin network. Once your transaction reaches **6 confirmations** (\~60 minutes), it transitions to the processing state.

You can poll for deposit status:

**Using cbtc-lib (Rust):**

```rust
use cbtc::mint_redeem::mint;

let status = mint::get_deposit_account_status(mint::GetDepositAccountStatusParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
 api_url: api_url.clone(),
 account_contract_id: deposit_account.contract_id.clone(),
}).await?;

println!("Bitcoin address: {} | Last processed block: {}",
 status.bitcoin_address, status.last_processed_bitcoin_block);
```

Step 6: Attestor Verification

This step is fully automated. The Attestor network:

1. Independently verifies the Bitcoin transaction has 6+ confirmations
2. Each Attestor submits a `ConfirmDepositAction` to the Canton governance module
3. Once the required threshold of confirmations is reached, the Coordinator executes the mint **No action is required from your application during this step.**

Step 7: CBTC Available

Your CBTC is minted and available in your Canton party. Check your balance:

**Using cbtc-lib (Rust):**

```rust
use cbtc::active_contracts;

let holdings = active_contracts::get(active_contracts::Params {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
}).await?;

println!("CBTC holdings: {} contract(s)", holdings.len());
```

***

## How to Burn CBTC: Redeem Wrapped Bitcoin for Native BTC

### How It Works

```mermaid
sequenceDiagram
 participant Dev as Your App
 participant Canton as Canton Ledger API
 participant Att as Attestor Network
 participant BTC as Bitcoin Network

 Dev->>Canton: 1. Create WithdrawAccount (set BTC destination address)
 Dev->>Canton: 2. Submit withdrawal against WithdrawAccount
 Canton->>Att: 3. Attestors verify and approve withdrawal
 Att->>Att: 4. FROST threshold signing of BTC transaction
 Att->>BTC: 5. Broadcast signed transaction
 BTC-->>Dev: 6. BTC arrives after 6 confirmations
```

### Step-by-Step

Step 1: Initiate a Burn

First, create a **WithdrawAccount** with your destination BTC address. The destination address is stored on the WithdrawAccount and can be updated later. Then submit the withdrawal against that account. Like deposit account creation, this requires your Minter credential contract IDs.

**Using cbtc-lib (Rust):**

```rust
use cbtc::mint_redeem::redeem;

// Step 1: Create a withdraw account
let withdraw_account = redeem::create_withdraw_account(redeem::CreateWithdrawAccountParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 account_rules_contract_id: rules.wa_rules.contract_id.clone(),
 account_rules_template_id: rules.wa_rules.template_id.clone(),
 account_rules_created_event_blob: rules.wa_rules.created_event_blob.clone(),
 destination_btc_address: btc_destination_address.clone(),
 credential_cids: minter_credential_cids.clone(),
}).await?;

// Step 2: Submit the withdrawal (burns CBTC, Attestor network processes BTC payout)
let updated_account = redeem::submit_withdraw(redeem::SubmitWithdrawParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 api_url: api_url.clone(),
 withdraw_account_contract_id: withdraw_account.contract_id.clone(),
 amount: cbtc::DamlDecimal::parse("0.001")?,
 holding_contract_ids: holding_ids,
 credential_cids: Some(minter_credential_cids.clone()),
}).await?;

println!("Withdrawal submitted. Pending balance: {}", updated_account.pending_balance);
```

> ℹ️ **Amounts are `DamlDecimal`.** Build them with `cbtc::DamlDecimal::parse`, which validates the value against Daml's decimal precision rules up front, so an unrepresentable amount fails locally instead of being rejected by the ledger. This applies to transfer and allocation amounts too.

Step 2: Attestor Verification and Signing

The Attestor network:

1. Verifies the burn request on Canton
2. Constructs the Bitcoin withdrawal transaction
3. Coordinates FROST threshold signing across Attestors
4. Once the signing threshold is met, broadcasts the signed transaction to the Bitcoin network **This step is fully automated. No action required.**

Step 3: Bitcoin Delivery

After the signed transaction is broadcast, wait for 6 Bitcoin confirmations. Your BTC will arrive at the specified destination address.

***

## Error Handling and Recovery Patterns for CBTC Integrations

> 🔧 **Error handling is critical for production integrations.** The CBTC system includes built-in resilience, but your application should handle these scenarios gracefully.

### Failed Broadcast

The system includes **automatic retry logic**. If a Bitcoin transaction fails to broadcast initially, the Coordinator detects the failure during subsequent periodic checks (every 60-120 seconds) and rebroadcasts using stored transaction data.

**What your app should do:** Monitor withdrawal status. If status remains in `broadcasting` for more than 10 minutes, log an alert for investigation.

### Insufficient Confirmations

If a deposit stalls below 6 confirmations (e.g., due to Bitcoin network congestion), the system simply waits. There is no timeout.

**What your app should do:** Display the current confirmation count to the user. Consider showing an estimated time based on current Bitcoin block times.

### Idempotency

Each withdrawal generates a **unique transaction ID** that prevents accidental double-spending, even if network issues cause retry attempts. The system is designed to be idempotent.

**What your app should do:** Store the withdrawal request ID and use it for status checks rather than initiating duplicate requests.

### Attestor Timeout

If governance approval is delayed (e.g., some Attestors are temporarily offline), the system continues to collect approvals. As long as the threshold can eventually be met, the operation will complete.

**What your app should do:** If a mint or burn is pending for more than 2 hours, escalate to BitSafe support.

### Partial Failure

If some Attestors approve but the threshold is not reached (e.g., too many Attestors offline simultaneously), the operation will remain pending until the threshold is met or the situation is resolved.

**What your app should do:** Alert your operations team. Contact <support@bitsafe.finance>.

***

## CBTC UTXO Management: Consolidation and Best Practices

> ⚠️ **Important for high-volume integrations.** Each CBTC transfer creates UTXOs. Canton recommends a maximum of **10 UTXOs per party**. Exceeding this causes increased load and fees on your node.

The cbtc-lib Rust library provides functions for managing UTXOs:

```rust
use cbtc::consolidate;

// Check UTXO count and consolidate if threshold exceeded
let result = consolidate::check_and_consolidate(consolidate::CheckConsolidateParams {
 party: party_id.clone(),
 threshold: 10, // Canton's soft limit
 ledger_host: ledger_host.clone(),
 access_token: access_token.clone(),
 registry_url: registry_url.clone(),
 decentralized_party_id: decentralized_party_id.clone(),
}).await?;

if result.consolidated {
 println!("Consolidated {} UTXOs into {}", result.utxos_before, result.utxos_after);
}
```

**Best practices:**

* Monitor UTXO count per party and consolidate proactively
* Batch transfers where possible to minimise UTXO creation
* If creating many parties, use the Ledger API directly (not wallet UI/API) - see [Canton docs](https://docs.digitalasset.com/build/3.4/tutorials/json-api/canton_and_the_json_ledger_api_ts.html#allocating-a-party)

***

## Escalation Path

| Situation                 | Action                                                                          |
| ------------------------- | ------------------------------------------------------------------------------- |
| Mint pending > 2 hours    | Check Bitcoin confirmations first. If 6+ confirmations reached, contact BitSafe |
| Burn pending > 2 hours    | Contact BitSafe engineering                                                     |
| Unexpected error from API | Retry with exponential backoff. If persistent, contact BitSafe                  |
| UTXO-related issues       | Use cbtc-lib consolidation functions. If unresolved, contact BitSafe            |

**Support channels:**

* **Email:** <support@bitsafe.finance>

***


# CBTC Overview

> ⚠️ **API Disclaimer:** CBTC APIs are subject to change. There is no formal versioning policy today. Breaking changes are communicated via the site changelog.

***

## What is CBTC? Bitcoin on the Canton Network

CBTC is a **1:1 wrapped Bitcoin token** built on the [Canton Network](https://www.canton.network/), a privacy-first blockchain for institutional finance. Each CBTC is fully backed by native BTC held in decentralized custody using FROST threshold signatures. CBTC is **CIP-56 compliant**, meaning it works with any Canton token-standard-compatible tool out of the box.

CBTC brings Bitcoin's liquidity into Canton's privacy-enabled smart contract environment, where app developers and trading firms can build trading, DeFi, custody, and settlement applications without exposing positions to a public mempool. Unlike wrapped Bitcoin on public chains, CBTC transactions are private by default, eliminating MEV (Maximal Extractable Value) risks like front-running and sandwich attacks.

**Key properties:**

| Property          | Value                                                                                                                   |
| ----------------- | ----------------------------------------------------------------------------------------------------------------------- |
| **Backing**       | 1 CBTC = 1 BTC, always                                                                                                  |
| **Standard**      | CIP-56 (Canton Instrument Protocol)                                                                                     |
| **Custody**       | Decentralized via FROST threshold signatures (no single party can move reserves)                                        |
| **Network**       | Canton Network (permissioned, private transactions)                                                                     |
| **Audit**         | [Quantstamp audit report](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html) |
| **Confirmations** | 6 Bitcoin block confirmations (\~60 minutes) for minting                                                                |

***

## CBTC Architecture: How Wrapped Bitcoin Works on Canton

The CBTC system bridges Bitcoin's UTXO model to Canton's Daml-based smart contract network through three layers:

### 1. Bitcoin Layer

Bitcoin transactions are monitored and verified. A user sends BTC to a generated Taproot deposit address. The system waits for 6 block confirmations before proceeding.

### 2. Attestor Network

A decentralised network of institutional-grade node operators independently verify Bitcoin deposits and withdrawals. Each Attestor runs nodes on **both** the Bitcoin and Canton networks. Key details:

* **Operators:** Pre-screened institutional node operators (including providers like Finoa and Nethermind)
* **Threshold:** A configurable M-of-N threshold of Attestors must approve every mint and burn operation
* **Coordination:** A Coordinator executes periodic checks (every 60-120 seconds), monitors deposit accounts, constructs Bitcoin transactions, and submits governance actions
* **No unilateral control:** No single party - including BitSafe or the Coordinator - can mint, burn, or move BTC without threshold approval

### 3. Canton Asset Layer

Daml contracts mint and burn CBTC tokens, but **only** after the required threshold of Attestor signatures is reached on the governance contract. CBTC is then held in the user's Canton party, fully under their control.

```mermaid
flowchart LR
 A["Bitcoin Network<br>(Taproot deposit address)"] -->|"6 confirmations"| B["Attestor Network<br>(FROST threshold signing)"]
 B -->|"M-of-N approval"| C["Canton Network<br>(Daml contracts mint CBTC)"]
 C -->|"Burn request"| B
 B -->|"Signed BTC tx"| A
```

***

## Security Model: FROST Threshold Signatures for Bitcoin Custody

CBTC's security rests on **FROST** (Flexible Round-Optimised Schnorr Threshold Signatures), a cryptographic protocol added to Bitcoin with the Taproot upgrade.

**Why FROST matters for developers:**

* **Taproot-native:** Deposit addresses are standard P2TR addresses. Any wallet that supports Taproot can send BTC to mint CBTC.
* **Indistinguishable on-chain:** FROST signatures look identical to regular single-signature Bitcoin transactions. No one can tell from the blockchain that a threshold scheme is in use.
* **Smaller transactions, lower fees:** Compared to traditional on-chain multisig, FROST produces a single aggregated signature regardless of how many Attestors participated.
* **No single point of failure:** Even if some Attestors go offline, the system continues to operate as long as the threshold is met. For a full technical deep dive, see the [Security Deep Dive](https://docs.bitsafe.finance/developers/security-deep-dive) page. For the original research, see the [FROST whitepaper](https://eprint.iacr.org/2020/852).

***

## What You Can Build with Wrapped Bitcoin on Canton

CBTC is a foundational layer for building institutional-grade financial products on Canton:

* **DeFi Protocols** - DEXs, lending platforms, and liquidity pools using CBTC as collateral
* **Custody and Wallet Solutions** - Institutional-grade wallets supporting CBTC and Canton-native assets
* **Structured Products** - Yield-generating vaults, options strategies, and derivatives
* **Payment and Settlement** - Instant, low-cost cross-border transactions
* **Trading Systems** - Spot and perpetual trading with Canton's privacy (no public mempool, no MEV)

***

## Developer Resources

| Resource              | Description                                           | Link                                                                                                                               |
| --------------------- | ----------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------- |
| **cbtc-lib (Rust)**   | SDK for minting, burning, sending, and receiving CBTC | [GitHub](https://github.com/DLC-link/cbtc-lib) · [Setup guide](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) |
| **canton-lib**        | Lower-level Canton interaction library                | [GitHub](https://github.com/DLC-link/canton-lib/)                                                                                  |
| **CBTC DAR files**    | Daml packages to install on your Canton participant   | [GitHub](https://github.com/DLC-link/cbtc-lib/tree/main/cbtc-dars)                                                                 |
| **FROST Whitepaper**  | Original threshold signature research                 | [ePrint](https://eprint.iacr.org/2020/852)                                                                                         |
| **Canton Whitepaper** | Canton Network technical overview                     | [canton.network](https://canton.network/)                                                                                          |
| **Quantstamp Audit**  | Security audit of CBTC smart contracts                | [View Report](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html)                        |
| **Data API**          | Analytics and rewards API for institutional clients   | [API Reference](https://docs.bitsafe.finance/developers/cbtc-api-reference)                                                        |

***

## Next Steps

* **Ready to code?** Start with [SDK Setup and Installation](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) to install `cbtc-lib` and configure your environment, then follow the [Developer Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start) to mint your first CBTC in 15 minutes
* **Need API details?** See the [API Reference](https://docs.bitsafe.finance/developers/cbtc-api-reference) for Canton Ledger API endpoints
* **Setting up authentication?** See the [Authentication Guide](https://docs.bitsafe.finance/developers/cbtc-authentication) for Keycloak setup (and an Auth0 community example)
* **Want to test first?** See the [Testnet Guide](https://docs.bitsafe.finance/developers/cbtc-testnet-guide) for sandbox environment setup

***


# CBTC Testnet Guide

> ⚠️ **API Disclaimer:** CBTC APIs are subject to change. Testnet behavior may differ from mainnet in some respects (see Parity section below).

***

## Overview: CBTC Testnet for Developers

The CBTC testnet is a sandbox environment where developers can experiment with the full mint, burn, and transfer lifecycle using **test BTC** with no real funds at risk. We recommend all integrations start on testnet before deploying to mainnet.

***

## How to Get Testnet CBTC: Three Options

### Option 1: CBTC Testnet Faucet (Recommended)

The fastest way to get testnet tokens:

[**CBTC Testnet Faucet →**](https://cbtc-faucet.bitsafe.finance/)

Simply enter your testnet wallet address and receive testnet CBTC and CC (for gas) instantly.

> 💡 **Quick and easy:** No setup required. Just enter your address and go.

### Option 2: Bron Wallet Testnet Environment

If the faucet is unavailable or you want a full testnet wallet environment:

1. **Create a new workspace** in [Bron Wallet](https://bron.app/)
2. Enable **Developer settings → Testnet mode** during workspace creation
3. **Create a testnet account** (toggle Testnet ON in account settings)
4. Select a **Trusted third party** (e.g., Qrypt) for key recovery
5. Use the faucet to fund your new testnet account

### Option 3: Mint via Testnet Flow

You can also mint testnet CBTC through the same flow as mainnet, using testnet BTC. This is useful for testing the full minting integration:

1. Set up your participant pointing at the **testnet** Canton network
2. Install CBTC DAR files
3. Follow the standard minting flow (see [Minting and Burning Guide](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning))
4. Use testnet BTC from a Bitcoin testnet faucet

***

## Testnet Environment Details

| Property                  | Testnet                                                                                             | Mainnet                                                                             |
| ------------------------- | --------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------- |
| **Registry URL**          | [`https://api.utilities.digitalasset-staging.com`](https://api.utilities.digitalasset-staging.com/) | [`https://api.utilities.digitalasset.com`](https://api.utilities.digitalasset.com/) |
| **Coordinator URL**       | [`https://testnet.dlc.link/attestor-1`](https://testnet.dlc.link/attestor-1)                        | [`https://mainnet.dlc.link/attestor-1`](https://mainnet.dlc.link/attestor-1)        |
| **Instrument ID (admin)** | `cbtc-network::12201b17...508f`                                                                     | `cbtc-network::12205af3...b262`                                                     |
| **BTC network**           | Bitcoin Testnet                                                                                     | Bitcoin Mainnet                                                                     |
| **Faucet**                | [cbtc-faucet.bitsafe.finance](https://cbtc-faucet.bitsafe.finance/)                                 | N/A (real BTC required)                                                             |

### Testnet Instrument ID (Full)

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-staging.com"
}
```

***

## Testnet vs. Mainnet: What Is the Same and What Differs

> 📋 Understanding what is the same and what differs between testnet and mainnet is critical for a smooth production launch.

### ✅ What Is Identical

* **DAR files:** Same CBTC Daml packages
* **API surface:** Same Canton Ledger API endpoints and Daml template interfaces
* **Mint and burn flows:** Same step-by-step process
* **Governance model:** Same Attestor threshold approval mechanism
* **Token standard:** CIP-56 compliant on both networks

### ⚠️ What Differs

* **Attestor set:** Testnet runs a **smaller** Attestor set than mainnet
* **Confirmation times:** May be faster on testnet due to less Bitcoin network congestion
* **Instrument IDs:** Different across networks - always fetch from the metadata URL, never hardcode
* **BTC:** Testnet uses test BTC with no real value
* **Faucet availability:** Testnet has a faucet; mainnet requires real BTC

### 🚫 What Is Mocked or Unavailable on Testnet

* **Real BTC settlement:** No real Bitcoin is involved
* **Production Attestor SLAs:** Testnet Attestors do not carry the same uptime guarantees
* **Mainnet fee structure:** Fees on testnet may not reflect production costs

***

## Important Operational Notes

> ⚠️ **Testnet may be reset without notice.** Do not rely on testnet state for production planning. Testnet CBTC balances and transaction history may not persist across resets.

* Testnet is for **development and testing only**
* Do not use testnet data for compliance, reporting, or production decisions
* Testnet performance is not indicative of mainnet performance

***

## Migrate from CBTC Testnet to Mainnet: Step-by-Step Checklist

When your testnet integration is working, the migration to mainnet involves:

1. **Update your participant config** to point at the mainnet Canton network
2. **Update Instrument IDs** to mainnet values (see [API Reference](https://docs.bitsafe.finance/developers/cbtc-api-reference))
3. **Update Coordinator URL** to [`https://mainnet.dlc.link/attestor-1`](https://mainnet.dlc.link/attestor-1)
4. **Use real BTC** for minting - the flow is identical
5. **Review authentication** - ensure your production OIDC provider is configured
6. **Test with a small amount first** - mint a minimal amount of CBTC on mainnet before going live

***

## Devnet

There is also a **devnet** environment for earlier-stage experimentation. Devnet is less stable than testnet and may be updated more frequently.

**Coordinator URL:** [`https://devnet.dlc.link/attestor-2`](https://devnet.dlc.link/attestor-2)

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-dev.com"
}
```

***

## Troubleshooting

| Issue                                 | Resolution                                                                    |
| ------------------------------------- | ----------------------------------------------------------------------------- |
| Faucet not working                    | Use Bron Wallet testnet setup (Option 2) or contact <support@bitsafe.finance> |
| Testnet CBTC balance disappeared      | Testnet may have been reset - request new tokens from the faucet              |
| Minting on testnet takes too long     | Check Bitcoin testnet block times - they can be irregular                     |
| Cannot connect to testnet participant | Verify your participant config points to the correct testnet endpoints        |

**Support:** <support@bitsafe.finance>

***


# Changelog

All notable changes to the CBTC developer documentation are logged here. This includes new pages, content updates, API changes, SDK version bumps, and corrections.

***

## 2026-02-10

### 🚀 Initial publication

* Published first draft of all CBTC developer documentation across 11 pages
* **New pages:** CBTC Overview, Quick Start, Minting and Burning, API Reference, Authentication, Integration Guides, Security Deep Dive, Technical Reference, Instrument ID Management, SDK Setup and Installation, Testnet Guide
* **SDK:** Documentation pinned to `cbtc-lib` v0.0.1 (post-December 2025 restructure)
* **Instrument IDs:** Published devnet, testnet, and mainnet IDs with metadata endpoint URLs
* **Known gaps:** Vaults documentation (Not Started), Home landing page (in progress), Error Codes Reference (deferred to v2)

***

## 2026-03-02

### 🔧 PR #22: Code and API corrections across all CBTC docs

Applied all corrections from [GitHub PR #22](https://github.com/DLC-link/cbtc-lib/pull/22) ("Fix CBTC docs to match actual cbtc-lib and canton-lib APIs"). Every Rust code example, curl command, module path, and function signature has been verified against the actual `cbtc` v0.3.0 and `canton-lib` v0.3.0 source code.

**Affected pages:** Quick Start, Minting and Burning, API Reference, Authentication, SDK Setup, Technical Reference

**Version and crate updates**

* SDK version updated from v0.0.1 to **v0.3.0** across all pages
* Crate name corrected from `cbtc-lib` / `cbtc_lib` to **`cbtc`**
* `canton-lib` documented as a **workspace** with 4 crates: `keycloak`, `ledger`, `registry`, `common` (all v0.3.0) **Authentication code**
* All auth examples updated from `keycloak::login(url, id, secret, user, pass)` to struct-based `keycloak::login::password(PasswordParams {... })` and `keycloak::login::client_credentials(ClientCredentialsParams {... })`
* Auth0 callout updated to reference correct function names (`keycloak::login::password`, `keycloak::login::client_credentials`) **Module paths and function names**
* `cbtc_lib::deposit` → `cbtc::mint_redeem::mint`
* `cbtc_lib::balance` → `cbtc::active_contracts`
* `cbtc_lib::withdraw` → `cbtc::mint_redeem::redeem`
* `cbtc_lib::utxo` → `cbtc::consolidate`
* `get_deposit_address` → `get_bitcoin_address`
* `get_active_contracts` → `active_contracts::get`
* `transfer::send` → `transfer::submit`
* `accept::accept_transfer` → `accept::submit`
* `redeem::burn_and_withdraw` → `redeem::create_withdraw_account` + `redeem::submit_withdraw` (two-step)
* `consolidate::check_consolidate` → `consolidate::check_and_consolidate`
* All function signatures updated from positional args to struct params **Environment variables**
* `KEYCLOAK_URL` replaced with `KEYCLOAK_HOST` + `KEYCLOAK_REALM`
* `KEYCLOAK_CLIENT_SECRET` removed from password flow examples
* `LEDGER_PORT` removed; all curl examples now use `${LEDGER_HOST}` only **Infrastructure URLs**
* Attester URLs corrected: `attestor.bitsafe.dev` → `devnet.dlc.link/attestor-1`, `attestor.bitsafe.testnet` → `testnet.dlc.link/attestor-1`, `attestor.bitsafe.com` → `mainnet.dlc.link/attestor-1` **Daml templates**
* `CBTC.Issuance:DepositAccount` → `CBTC.DepositAccount:CBTCDepositAccount`
* Added `CBTC.WithdrawAccount:CBTCWithdrawAccount` to API Reference **SDK Setup additions**
* Added `cbtc::accept` and `cbtc::cancel_offers` to key modules table
* Added client credentials authentication example
* Added verification script, migration guide, and example.env file

### ✏️ Spelling correction: Attestor → Attester

Per reviewer feedback, corrected "Attestor" to "Attester" across all pages where it appeared in prose.

**Affected pages:** Quick Start, Minting and Burning, Security Deep Dive

### 🔒 Security Deep Dive: Attester network composition

Corrected the Attester network composition per reviewer input:

* **Before:** 9 pre-screened external node operators (including P2P and Everstake) + 1 BitSafe
* **After:** 3 external node operators (Finoa, Nethermind, DSRV) + 1 BitSafe-operated node (4 total)

### 📋 Integration Guides: Partner and feature updates

* Silvana listed as *(coming soon)* pending verification
* Hosted UI option updated from "coming soon" to *(coming soon)* per product team input

### 💰 Technical Reference: Fee confirmation

* Mint and burn fees confirmed at **0%** (changed from yellow warning callout to green confirmed callout)

***

## 2026-07-27

### 🔢 SDK and DAR version corrections

Version references had drifted out of sync with the released libraries, and three pages each stated a different `cbtc-lib` version. All version references now match the released tags.

**Corrected to actual released versions**

* `cbtc-lib` → **v0.6.4** (previously stated as v0.3.1 on API Reference, v0.4.2 on SDK Setup and Technical Reference, v0.3.0 on Quick Start)
* `canton-lib` crates `keycloak`, `ledger`, `registry`, `common` → **v0.6.1** (previously v0.3.1 / v0.5.0)
* Latest CBTC DAR → **`cbtc-1.2.1`**, shipped in `cbtc-lib` v0.6.4

**Affected pages:** SDK Setup and Installation, API Reference, Technical Reference

**Other fixes in this pass**

* API Reference install snippet corrected from `https://` to `ssh://` transport, matching SDK Setup — the HTTPS form does not work for this private repository
* DAR download links repointed from the `v0.3.1` and `v0.4.2` tags to `v0.6.4`
* Technical Reference repository table had `cbtc-lib` listed twice; the second row now correctly describes the CBTC DAR
* Clarified that the DAR version (`cbtc-1.2.1`) and the crate version (`v0.6.4`) are numbered independently, which was the likely source of the confusion
* Added a note that canton-lib crates must be pinned to the same tag `cbtc-lib` depends on, to avoid Cargo resolving two incompatible copies of the same types

**Removed the December 2025 restructure migration content**

## The "Migration Guide: December 2025 Restructure" section on SDK Setup, and the matching restructure note on the API Reference, described how the library used to be laid out. Both pages document how to use the current release, so the guidance now lives here in the changelog and in the [cleanup PR](https://github.com/DLC-link/cbtc-lib/pull/11) instead. The restructure moved module paths and function signatures only, with no runtime behaviour changes; code written before it needs its `use` statements updated to the module paths listed on SDK Setup.


# Instrument ID Management

***

## What Are Instrument IDs?

Every token on Canton is identified by an **Instrument ID**, a combination of an **admin** party ID and a token **id** string, plus a **registry URL**. These values let any CIP-56-compliant tool discover and interact with CBTC.

***

## Why IDs Change

Instrument IDs can change due to network dynamics, including DAR upgrades, network migrations, or infrastructure changes. **Never hardcode Instrument IDs.** Fetch them dynamically from the metadata URL.

> ⚠️ There is currently **no push notification** when Instrument IDs change. Poll the metadata URL periodically.

***

## Current IDs by Network

### Devnet

* **Registry URL:** [`https://api.utilities.digitalasset-dev.com`](https://api.utilities.digitalasset-dev.com/)
* **Coordinator URL:** [`https://devnet.dlc.link/attestor-2`](https://devnet.dlc.link/attestor-2)
* **Metadata:** [View](https://api.utilities.digitalasset-dev.com/api/token-standard/v0/registrars/cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff/registry/metadata/v1/instruments)

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-dev.com"
}
```

### Testnet

* **Registry URL:** [`https://api.utilities.digitalasset-staging.com`](https://api.utilities.digitalasset-staging.com/)
* **Coordinator URL:** [`https://testnet.dlc.link/attestor-1`](https://testnet.dlc.link/attestor-1)
* **Metadata:** [View](https://api.utilities.digitalasset-staging.com/api/token-standard/v0/registrars/cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f/registry/metadata/v1/instruments)

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset-staging.com"
}
```

### Mainnet

* **Registry URL:** [`https://api.utilities.digitalasset.com`](https://api.utilities.digitalasset.com/)
* **Coordinator URL:** [`https://mainnet.dlc.link/attestor-1`](https://mainnet.dlc.link/attestor-1)
* **Metadata:** [View](https://api.utilities.digitalasset.com/api/token-standard/v0/registrars/cbtc-network::12205af3b949a04776fc48cdcc05a060f6bda2e470632935f375d1049a8546a3b262/registry/metadata/v1/instruments)

```json
{
 "instrument_id": {
 "admin": "cbtc-network::12205af3b949a04776fc48cdcc05a060f6bda2e470632935f375d1049a8546a3b262",
 "id": "CBTC"
 },
 "registry_url": "https://api.utilities.digitalasset.com"
}
```

***

## Recommended Polling Pattern

```rust
use std::time::Duration;

// Poll every 5 minutes in production
const POLL_INTERVAL: Duration = Duration::from_secs(300);

async fn refresh_instrument_id(registry_url: &str, admin: &str) -> Result<InstrumentId> {
 let url = format!(
 "{}/api/token-standard/v0/registrars/{}/registry/metadata/v1/instruments",
 registry_url, admin
 );
 let response = reqwest::get(&url).await?.json::<InstrumentMetadata>().await?;
 Ok(response.instrument_id)
}
```

**Best practices:**

* Cache the Instrument ID locally and refresh on a schedule (every 5-15 minutes)
* Log a warning if the ID changes between polls, as this may indicate a DAR upgrade
* On startup, always fetch fresh rather than relying on cached values
* Handle fetch failures gracefully and use the last known good value

***

## Token Standard API Reference

Full documentation for the Canton Token Standard API: [Canton Token Standard Docs](https://docs.dev.sync.global/app_dev/token_standard/index.html#api-references)

**Requirements:** CBTC is CIP-56 compliant. No special requirements for holding CBTC.

***


# Integration Guides

> ⚠️ **API Disclaimer:** CBTC APIs are subject to change. Label all examples with the SDK version and DAR version they were tested against.

***

## Overview

This page provides integration patterns for common CBTC use cases. Each pattern includes architecture notes, key considerations, and pointers to relevant code. For API details, see the [API Reference](https://docs.bitsafe.finance/developers/cbtc-api-reference). For authentication setup, see the [Authentication Guide](https://docs.bitsafe.finance/developers/cbtc-authentication).

***

## Integration Pattern 1: DeFi Protocol

**Use case:** Build a DEX, lending platform, or liquidity pool using CBTC as collateral.

### Architecture

1. Your protocol runs on a Canton participant node with CBTC DAR files installed
2. Users deposit CBTC into your protocol's Canton party via a `Transfer` choice
3. Your protocol logic (Daml contracts) manages positions, collateral, and settlement
4. Users withdraw CBTC back to their own party when exiting

### Key Considerations

* **UTXO management:** Each transfer creates UTXOs. Keep below 10 per party. Use `cbtc-lib` consolidation functions.
* **Instrument ID:** Fetch dynamically - see [Instrument ID Management](https://docs.bitsafe.finance/developers/instrument-id-management)
* **Privacy:** Canton transactions are private by default. Only parties to a contract see its details. This eliminates MEV.
* **Transfer costs:** \~$3-5 per CBTC transfer on Canton currently. Factor this into your protocol economics.

### Example Partners

* **Bron** - BTC-CBTC and CC-CBTC swapping on Canton
* **Elk Capital Markets / Triangle** - OTC and app-based CBTC trading
* **Silvana** - DEX/trading venue on Canton *(coming soon)*

***

## Integration Pattern 2: Wallet or Custody Solution

**Use case:** Support CBTC in an institutional-grade wallet or custody platform.

### Architecture

1. Wallet connects to a Canton participant via the Ledger API
2. Authentication via OIDC (Keycloak supported, Auth0 community example available)
3. CBTC balances queried via `state-queries` endpoint
4. Transfers executed via `Transfer` choice on CBTC token contracts

### Supported Wallets (Current Ecosystem)

* **Loop Wallet** - Canton-native wallet with CBTC support
* **Console / Zoro Wallet** - Canton wallet with API access
* **Bron Wallet** - Multi-party wallet with testnet support
* **WalletConnect** - For dApp-to-wallet connections

### Key Considerations

* **External signing:** Available for integration with custody providers (DFNS, Fordefi, Ledger)
* **Party creation at scale:** If creating 10+ parties, use the Ledger API directly rather than wallet UI - see [Canton docs](https://docs.digitalasset.com/build/3.4/tutorials/json-api/canton_and_the_json_ledger_api_ts.html#allocating-a-party)
* **CORS:** If your wallet makes browser-based API calls, configure CORS on your ingress

***

## Integration Pattern 3: Trading System

**Use case:** Build spot trading, perpetual contracts, options, or structured products with CBTC.

### Why Canton for Trading

* **No public mempool** - positions are not visible to other participants, eliminating front-running and sandwich attacks (MEV)
* **Private transactions** - only parties to a trade see the details
* **Audit-ready** - Canton's privacy model supports selective disclosure for compliance

### Architecture

1. Trading engine runs as Daml contracts on Canton
2. CBTC used as settlement or collateral asset
3. Counterparty discovery and matching handled by your protocol
4. Settlement is atomic - either both sides complete or neither does

### Example: Options on CBTC

CBTC holders can write covered CALL options, earning premium income while maintaining BTC exposure. Settlement uses Canton's atomic dual-token transfer - the buyer receives the underlying asset while the seller receives payment, atomically.

### DvP Settlement Using Allocations

For atomic delivery-versus-payment, `cbtc-lib` provides the `cbtc::allocation` module, which implements the Canton Token Standard allocation lifecycle. This is the mechanism behind the atomic settlement described above.

**How it differs from a standard transfer.** The two-phase `transfer` / `accept` flow described in the [Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start) is **free-of-payment (FOP)**: the sender offers CBTC, the receiver accepts, and nothing is exchanged in return. There is no linkage to a second leg. An **allocation** instead locks CBTC into one leg of a multi-leg settlement that a third party settles atomically, so the CBTC only moves if the other leg moves too.

|                        | FOP transfer (`cbtc::transfer` + `cbtc::accept`) | DvP allocation (`cbtc::allocation`)                   |
| ---------------------- | ------------------------------------------------ | ----------------------------------------------------- |
| **Parties**            | Sender, receiver                                 | Sender, receiver, **settlement executor** (the venue) |
| **Settled by**         | The receiver, by accepting                       | The executor, across all legs at once                 |
| **Atomicity**          | Single leg only                                  | All legs settle together or none do                   |
| **Sender can reclaim** | Cancel the offer (`cbtc::cancel_offers`)         | Withdraw the allocation before settlement             |
| **Deadlines**          | `execute_before`                                 | `allocate_before`, then `settle_before`               |

**Lifecycle.** The sender locks their leg, then the executor settles:

1. **Allocate** - the leg sender calls `cbtc::allocation::allocate`, which exercises `AllocationFactory_Allocate` and locks the sender's holdings. If no input holdings are specified, the library auto-selects them.
2. **Execute** - the settlement executor calls `cbtc::allocation::execute_transfer` (`Allocation_ExecuteTransfer`). A coordinating app normally settles every leg together in a single transaction; the library exposes the single-leg choice for that purpose.
3. **Or unwind** - the sender can call `cbtc::allocation::withdraw` (`Allocation_Withdraw`) to reclaim locked holdings before settlement, and `cbtc::allocation::cancel` (`Allocation_Cancel`) releases them back to the sender.

**Timing.** An allocation must be funded before `allocate_before` and settled before `settle_before`, which must be the later of the two.

Allocating CBTC into a settlement leg:

```rust
use cbtc::allocation;

let allocation_spec = common::allocation::AllocationSpecification {
 settlement: common::allocation::SettlementInfo {
 executor: executor_party_id.clone(), // the venue settling the legs
 settlement_ref: common::allocation::Reference {
 id: settlement_ref_id.clone(),
 cid: None,
 },
 requested_at: now.to_rfc3339(),
 allocate_before: (now + chrono::Duration::hours(24)).to_rfc3339(),
 settle_before: (now + chrono::Duration::hours(48)).to_rfc3339(),
 meta: common::allocation::Metadata::default(),
 },
 transfer_leg_id: "leg0".to_string(),
 transfer_leg: common::allocation::TransferLeg {
 sender: sender_party_id.clone(),
 receiver: receiver_party_id.clone(),
 amount: cbtc::DamlDecimal::parse("0.1")?,
 instrument_id: common::transfer::InstrumentId {
 admin: decentralized_party_id.clone(),
 id: "CBTC".to_string(),
 },
 meta: common::allocation::Metadata::default(),
 },
};

allocation::allocate(allocation::Params {
 allocation: allocation_spec,
 requested_at: now.to_rfc3339(),
 input_holding_cids: Vec::new(), // empty = library auto-selects the sender's holdings
 ledger_host: ledger_host.clone(),
 access_token: access_token.clone(),
 registry_url: registry_url.clone(),
 decentralized_party_id: decentralized_party_id.clone(),
}).await?;
```

Reclaiming an allocation before settlement:

```rust
use cbtc::allocation;

allocation::withdraw(allocation::ActionParams {
 allocation_contract_id: allocation_cid.clone(),
 actor_party: sender_party_id.clone(),
 ledger_host: ledger_host.clone(),
 access_token: access_token.clone(),
 registry_url: registry_url.clone(),
 decentralized_party_id: decentralized_party_id.clone(),
}).await?;
```

> 💡 **No Minter credential needed.** Allocations move existing CBTC rather than creating or destroying it, so they do not require the Minter credential that minting and burning do.

A complete runnable example is in the library: [`examples/allocate_cbtc.rs`](https://github.com/DLC-link/cbtc-lib/blob/v0.6.4/examples/allocate_cbtc.rs). For the underlying standard, see the [Canton Token Standard allocation docs](https://docs.dev.sync.global/app_dev/token_standard/index.html).

***

## Integration Pattern 4: Minting Integration

**Use case:** Offer CBTC minting as a service to your users.

### Three Options

| Option                           | Description                                               | Effort                    |
| -------------------------------- | --------------------------------------------------------- | ------------------------- |
| **1. Direct API**                | Install CBTC DAR, call Canton APIs to mint/redeem         | Low - a few hours         |
| **2. Self-hosted UI**            | Install DAR + BitSafe minting UI locally                  | Medium - more maintenance |
| **3. Hosted UI** *(coming soon)* | Use BitSafe's centrally hosted UI against your validator. | TBD                       |

For Option 1, see the [Minting and Burning Guide](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) and [API Reference](https://docs.bitsafe.finance/developers/cbtc-api-reference).

For Options 2 and 3, contact BitSafe for setup details.

***

## Getting Started

1. **Install the SDK and DAR files** - see [SDK Setup and Installation](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) for `cbtc-lib`, `canton-lib`, DAR upload, and environment configuration
2. **Set up testnet first** - see [Testnet Guide](https://docs.bitsafe.finance/developers/cbtc-testnet-guide)
3. **Mint your first CBTC** - see [Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start)
4. **Review examples** - [GitHub examples](https://github.com/DLC-link/cbtc-lib/tree/main/examples) **Need help?** Reach out via <support@bitsafe.finance>

***


# Resources

***

## Glossary

| Term                        | Definition                                                                                                                                      |
| --------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------- |
| **CBTC**                    | Canton Bitcoin - a 1:1 wrapped BTC token on the Canton Network, issued and redeemed via a decentralised bridge.                                 |
| **Canton Network**          | A permissioned blockchain built by Digital Asset for institutional finance. Private transactions, no public mempool.                            |
| **CIP-56**                  | Canton Instrument Protocol - the token standard CBTC complies with, enabling interoperability with any CIP-56-compliant tool.                   |
| **Daml**                    | The smart contract language used on Canton. CBTC operations are Daml contract choices.                                                          |
| **DAR file**                | Daml Archive - a compiled Daml package that you install on your Canton participant to interact with CBTC contracts.                             |
| **FROST**                   | Flexible Round-Optimised Schnorr Threshold Signatures - the cryptographic protocol securing CBTC's Bitcoin custody.                             |
| **Attestor**                | An independent node operator that verifies Bitcoin transactions and participates in threshold signing for CBTC mint/burn operations.            |
| **Coordinator**             | A service that facilitates Attestor coordination, monitors deposits, and constructs Bitcoin transactions. Cannot act unilaterally.              |
| **Minter**                  | A credential granting the right to create deposit accounts and initiate CBTC minting.                                                           |
| **Instrument ID**           | The unique identifier for CBTC on a given Canton network (devnet/testnet/mainnet). Differs per environment.                                     |
| **Taproot (P2TR)**          | A Bitcoin address type introduced with the Taproot upgrade. Required for CBTC deposit addresses.                                                |
| **UTXO**                    | Unspent Transaction Output. Each CBTC transfer creates UTXOs. Canton recommends max 10 per party.                                               |
| **Decentralized Party**     | A Canton-native construct where multiple independent operators collectively control a party via threshold signing.                              |
| **ERC-4626**                | A tokenised vault standard. BitSafe Vaults implement ERC-4626 semantics on Canton.                                                              |
| **Curator**                 | A professional asset manager who operates yield strategies within a BitSafe Vault.                                                              |
| **LP (Liquidity Provider)** | An institutional depositor who provides capital to a Vault in exchange for shares and yield.                                                    |
| **MEV**                     | Maximal Extractable Value - front-running and sandwich attacks possible on public blockchains. Canton eliminates this via private transactions. |

***

## GitHub Repositories

* **cbtc-lib** (Rust SDK) - [github.com/DLC-link/cbtc-lib](https://github.com/DLC-link/cbtc-lib)
* **canton-lib** (lower-level Canton library) - [github.com/DLC-link/canton-lib](https://github.com/DLC-link/canton-lib)
* **cbtc-lib** (DAR files, scripts) - [github.com/DLC-link/cbtc-lib](https://github.com/DLC-link/cbtc-lib)
* **Code examples** - [github.com/DLC-link/cbtc-lib/tree/main/examples](https://github.com/DLC-link/cbtc-lib/tree/main/examples)

***

## Audit Reports

* [**Quantstamp Audit Report (CBTC)**](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html)

***

## Whitepapers and Research

* [**FROST: Flexible Round-Optimized Schnorr Threshold Signatures**](https://eprint.iacr.org/2020/852) - Komlo & Goldberg, 2020
* [**Canton Network Whitepaper**](https://www.canton.network/whitepapers) - Digital Asset

***

## Canton Ecosystem Links

* [Canton Network](https://www.canton.network/)
* [Canton Developer Documentation](https://docs.digitalasset.com/)
* [Canton Token Standard API](https://docs.dev.sync.global/app_dev/token_standard/index.html#api-references)
* [BitSafe Technical Docs (live site)](https://docs.bitsafe.finance/bitsafe-documentation/product-suite/cbtc)

***

## Support

> 📬 **Developer support:** <support@bitsafe.finance>

***

## Changelog

***


# SDK Setup and Installation

> ⚠️ **API Disclaimer.** CBTC APIs have no formal versioning policy today. All SDK interfaces described in this guide are **subject to change**. Breaking changes are communicated via the changelog.

***

This page is your single reference for installing and configuring everything you need to build with CBTC. If you've already completed setup, head straight to the [Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start) to mint your first wrapped Bitcoin.

***

## System Requirements

| Requirement                 | Details                                                                                                                                                                              |
| --------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| **Rust toolchain**          | Latest stable. Install via [rustup.rs](https://rustup.rs/)                                                                                                                           |
| **Canton participant node** | Running and connected to devnet, testnet, or mainnet. See [Canton documentation](https://docs.digitalasset.com/canton)                                                               |
| **DA Registry Utility**     | Installed and configured. See [Digital Asset Utilities docs](https://docs.digitalasset.com/utilities/mainnet/index.html)                                                             |
| **Keycloak credentials**    | Host, realm, client ID, username, and password for your environment                                                                                                                  |
| **Party ID**                | Your Canton Party ID, obtained during onboarding                                                                                                                                     |
| **Minter credential**       | Only required to **mint or burn** CBTC. Issued to your party by the CBTC registrar; request one via <sales@bitsafe.finance>. Holding, sending, and receiving CBTC do not require it. |

***

## Install cbtc-lib (Rust)

`cbtc-lib` is BitSafe's primary SDK for CBTC operations: minting, burning, transferring, UTXO management, and balance queries. It wraps the Canton Ledger API with type-safe Rust functions.

* **Repository:** [github.com/DLC-link/cbtc-lib](https://github.com/DLC-link/cbtc-lib)
* **Current version:** v0.6.4
* **Licence:** *Check repository*

### Add to your project

Add `cbtc-lib` to your `Cargo.toml`:

```toml
[dependencies]
cbtc = { git = "ssh://git@github.com/DLC-link/cbtc-lib.git", tag = "v0.6.4" }
```

> 📌 **Pin your version.** Always reference a specific tag (e.g. `v0.6.4`) rather than `main`. The library is under active development and `main` may contain breaking changes between releases.

### Key modules

| Module                      | Purpose                                                          |
| --------------------------- | ---------------------------------------------------------------- |
| `cbtc::mint_redeem::mint`   | Create deposit accounts, get Bitcoin deposit addresses           |
| `cbtc::mint_redeem::redeem` | Create withdraw accounts, burn CBTC and withdraw to BTC          |
| `cbtc::transfer`            | Send CBTC to another party (creates transfer offer)              |
| `cbtc::accept`              | Accept incoming CBTC transfer offers                             |
| `cbtc::active_contracts`    | Query current CBTC holdings for a party                          |
| `cbtc::consolidate`         | Merge multiple UTXO holdings into fewer contracts                |
| `cbtc::split`               | Split a single holding into multiple UTXOs                       |
| `cbtc::batch`               | Batch operations for sending to multiple recipients              |
| `cbtc::distribute`          | Distribute CBTC across multiple parties                          |
| `cbtc::cancel_offers`       | Cancel pending outgoing transfer offers                          |
| `cbtc::credentials`         | List and accept Minter credentials (required to mint or burn)    |
| `cbtc::allocation`          | Allocate CBTC into DvP settlement legs (delivery-versus-payment) |

***

## Install canton-lib

`canton-lib` is now a **Rust workspace** containing multiple crates that `cbtc` depends on. It handles Canton Ledger API communication, authentication, and Daml contract interactions.

* **Repository:** [github.com/DLC-link/canton-lib](https://github.com/DLC-link/canton-lib)
* **Crates:** `keycloak`, `ledger`, `registry`, `common` (all at v0.6.1)

### Add to your project

Add the canton-lib crates you need to your `Cargo.toml`:

```toml
[dependencies]
keycloak = { git = "ssh://git@github.com/DLC-link/canton-lib.git", tag = "v0.6.1" }
ledger = { git = "ssh://git@github.com/DLC-link/canton-lib.git", tag = "v0.6.1" }
registry = { git = "ssh://git@github.com/DLC-link/canton-lib.git", tag = "v0.6.1" }
common = { git = "ssh://git@github.com/DLC-link/canton-lib.git", tag = "v0.6.1" }
```

> 📌 **Match the tag `cbtc-lib` depends on.** `cbtc-lib` v0.6.4 pins canton-lib v0.6.1. If you add these crates at a different tag than the one `cbtc-lib` uses, Cargo will resolve two incompatible copies of the same types and your build will fail with confusing mismatched-type errors.

The `keycloak` crate provides authentication helpers used across all CBTC operations.

**Password-grant authentication** (for user-facing flows):

```rust
use keycloak::login::{password, password_url, PasswordParams};

let auth = password(PasswordParams {
 client_id: keycloak_client_id.clone(),
 username: keycloak_username.clone(),
 password: keycloak_password.clone(),
 url: password_url(&keycloak_host, &keycloak_realm),
}).await?;

let access_token = auth.access_token;
```

**Client credentials authentication** (for service-to-service / backend flows):

```rust
use keycloak::login::{client_credentials, client_credentials_url, ClientCredentialsParams};

let auth = client_credentials(ClientCredentialsParams {
 url: client_credentials_url("https://your-keycloak-host", "your-realm"),
 client_id: "your-client-id".to_string(),
 client_secret: "your-client-secret".to_string(),
}).await?;

let access_token = auth.access_token;
```

***

## Install CBTC DAR Files

DAR (Daml Archive) files contain the smart contract templates that power CBTC on Canton. They must be installed on your participant node before you can interact with CBTC.

**Download:** [github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars](https://github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars)

The latest CBTC DAR is **`cbtc-1.2.1`**, shipped in `cbtc-lib` v0.6.4. DAR versions and crate versions are numbered independently.

Install the DAR files on your Canton participant node using the Canton console or your deployment tooling. The specific installation method depends on your Canton setup. Refer to the [Canton documentation](https://docs.digitalasset.com/canton) for details.

> 💡 **Install every DAR version, not just the newest.** The repository ships all released DARs (`cbtc-1.0.0` through `cbtc-1.2.1`). Older versions are required to interact with contracts still live on the network from earlier releases. You can verify what your participant is missing with the `cbtc::dar_check` module.

> 💡 **DAR version and Instrument IDs are linked.** When DAR files are upgraded on the network, Instrument IDs may change. Always fetch Instrument IDs dynamically from the metadata endpoint rather than hardcoding them. See the [Instrument ID Management](https://docs.bitsafe.finance/developers/instrument-id-management) page for the polling pattern.

***

## Environment Configuration

Set these variables before running any CBTC commands or code. Values differ per environment.

| Variable                 | Devnet                                                                                      | Testnet                                                                                             | Mainnet                                                                             |
| ------------------------ | ------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------- |
| `REGISTRY_URL`           | [`https://api.utilities.digitalasset-dev.com`](https://api.utilities.digitalasset-dev.com/) | [`https://api.utilities.digitalasset-staging.com`](https://api.utilities.digitalasset-staging.com/) | [`https://api.utilities.digitalasset.com`](https://api.utilities.digitalasset.com/) |
| `BITSAFE_API_URL`        | [`https://api.devnet.bitsafe.finance`](https://api.devnet.bitsafe.finance)                  | [`https://api.testnet.bitsafe.finance`](https://api.testnet.bitsafe.finance)                        | [`https://api.mainnet.bitsafe.finance`](https://api.mainnet.bitsafe.finance)        |
| `DECENTRALIZED_PARTY_ID` | *Provided during onboarding*                                                                | *Provided during onboarding*                                                                        | *Provided during onboarding*                                                        |

> 💡 **`BITSAFE_API_URL`** is the BitSafe API gateway, which serves the `/cbtc/v1/*` endpoints behind deposit accounts, deposit addresses, and withdrawals. `cbtc-lib` reads it and passes it as the `api_url` parameter to `get_account_contract_rules`, `get_bitcoin_address`, and `submit_withdraw`. An Attestor or Coordinator host will not work in its place.

### Example.env file

```bash
# Environment (choose one: devnet, testnet, mainnet)
REGISTRY_URL="https://api.utilities.digitalasset-staging.com"
BITSAFE_API_URL="https://api.testnet.bitsafe.finance"
CANTON_NETWORK="canton-testnet"
PARTY_ID="your-party-id"

# Authentication (Keycloak)
KEYCLOAK_HOST="https://your-keycloak-host"
KEYCLOAK_REALM="your-realm"
KEYCLOAK_CLIENT_ID="your-client-id"
KEYCLOAK_USERNAME="your-username"
KEYCLOAK_PASSWORD="your-password"

# Canton participant
LEDGER_HOST="https://your-ledger-host"
```

***

## Verify Your Installation

Run this minimal check to confirm everything is wired up:

```rust
use keycloak::login::{password, password_url, PasswordParams};
use cbtc::active_contracts;

#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
 // 1. Authenticate
 let auth = password(PasswordParams {
 client_id: std::env::var("KEYCLOAK_CLIENT_ID")?,
 username: std::env::var("KEYCLOAK_USERNAME")?,
 password: std::env::var("KEYCLOAK_PASSWORD")?,
 url: password_url(
 &std::env::var("KEYCLOAK_HOST")?,
 &std::env::var("KEYCLOAK_REALM")?,
 ),
 }).await?;

 println!("✅ Authenticated successfully");

 // 2. Query holdings (should return empty if no CBTC yet)
 let holdings = active_contracts::get(active_contracts::Params {
 ledger_host: std::env::var("LEDGER_HOST")?,
 party: std::env::var("PARTY_ID")?,
 access_token: auth.access_token,
 }).await?;

 println!("✅ Connected to Canton. Current CBTC holdings: {}", holdings.len());
 Ok(())
}
```

If both checks pass, you're ready. Head to the [Quick Start](https://docs.bitsafe.finance/developers/cbtc-quick-start) to mint your first CBTC.

***

## Next Steps

* [**Quick Start**](https://docs.bitsafe.finance/developers/cbtc-quick-start) - Mint your first wrapped Bitcoin in 15 minutes
* [**CBTC Minting and Burning**](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) - The mint and burn lifecycle in depth, with error handling and recovery patterns
* [**API Reference**](https://docs.bitsafe.finance/developers/cbtc-api-reference) - Full Canton Ledger API endpoint documentation
* [**Instrument ID Management**](https://docs.bitsafe.finance/developers/instrument-id-management) - How to fetch and poll for the latest CBTC Instrument IDs
* [**Authentication Guide**](https://docs.bitsafe.finance/developers/cbtc-authentication) - Detailed Keycloak setup and Auth0 community example
* [**Testnet Guide**](https://docs.bitsafe.finance/developers/cbtc-testnet-guide) - Get testnet CBTC from the faucet and test before going live

***


# Security Deep Dive

***

## Overview

CBTC's security model is built on three pillars: **FROST threshold signatures** on the Bitcoin side, a **decentralised Attestor Network** bridging both chains, and **Daml smart contracts** governing all operations on Canton. This page covers each in detail.

***

## FROST Threshold Signatures

CBTC uses **FROST** (Flexible Round-Optimised Schnorr Threshold Signatures), a cryptographic protocol formalised in [Komlo & Goldberg, 2020](https://eprint.iacr.org/2020/852) and enabled on Bitcoin via the **Taproot** upgrade.

### How FROST Works

FROST is a **two-round signing protocol:**

1. **Round One (Commitment):** The Coordinator selects the message to be signed and the set of participating Attestors. Each Attestor generates fresh nonces and public commitments, sent to the Coordinator.
2. **Round Two (Signature Share):** The Coordinator broadcasts all commitments. Each Attestor verifies them, computes an individual signature share, and sends it back. The Coordinator aggregates shares into a single valid Schnorr signature.

### Why FROST for CBTC

* **Taproot-native:** FROST signatures are standard Schnorr signatures, compatible with any Taproot (P2TR) wallet. No special wallet support needed.
* **Indistinguishable on-chain:** A FROST threshold signature looks identical to a single-signer Schnorr signature. No one can determine from the blockchain that a threshold scheme was used.
* **Smaller and cheaper:** One aggregated signature regardless of threshold size, versus N signatures for traditional on-chain multisig. Lower transaction fees.
* **No single point of failure:** The signing key is never reconstructed. Each Attestor holds only a share.

### Security Properties

* **Unforgeability:** No coalition below the threshold can produce a valid signature, even with adaptive corruption (formally proven in the ePrint paper)
* **Robustness against forgery attacks:** FROST mitigates certain Schnorr-specific threshold forgery vectors
* **Forget-and-Forgive protection:** The resharing protocol includes acknowledgement steps preventing split-group attacks during key rotation **Full paper:** [FROST: Flexible Round-Optimized Schnorr Threshold Signatures (ePrint 2020/852)](https://eprint.iacr.org/2020/852)

***

## Attestor Network

The Attestor Network is the decentralised security backbone of CBTC.

### Composition

* **3 external node operators** (Finoa, Nethermind, DSRV)
* **1 BitSafe-operated node** (4 total)
* Each Attestor runs nodes on **both** the Bitcoin and Canton networks

### Responsibilities

Attestor responsibilities are **almost entirely automated:**

* Independent verification of Bitcoin transactions reaching 6 confirmations
* Submission of `ConfirmDepositAction` (for mints) and `ArchiveWithdrawRequest` (for burns) to the Canton governance module
* Participation in FROST threshold signing for Bitcoin withdrawal transactions
* Monitoring deposit accounts and withdrawal requests The only manual process is **governance** - adding or removing Attestor nodes, which requires coordination between operators.

### Threshold Governance

* For critical actions (minting, burning), each Attestor submits confirmation **independently**
* Confirmations are recorded as Canton contracts
* Once the number of valid confirmations meets the **predefined threshold**, the Coordinator executes the action
* **No single party** - including BitSafe or the Coordinator - can unilaterally mint, burn, or move BTC

### Coordinator Role

The Coordinator is a service (which can be an Attestor or a separate non-signing entity) that:

* Executes periodic checks every **60-120 seconds**
* Monitors deposit accounts for new Bitcoin transactions
* Constructs Bitcoin transactions for withdrawals
* Submits governance actions to Canton
* Coordinates the FROST signing rounds **The Coordinator cannot act unilaterally.** It facilitates the process but requires threshold approval for every action.

***

## Dual-Network Security Model

CBTC's security spans two networks simultaneously:

| Layer                           | Network    | Security Mechanism                         |
| ------------------------------- | ---------- | ------------------------------------------ |
| **Bitcoin custody**             | Bitcoin L1 | FROST threshold signatures (Taproot)       |
| **Governance and coordination** | Canton     | Daml contracts with threshold confirmation |
| **Token operations**            | Canton     | CIP-56 compliant Daml contracts            |

The same Attestor network secures both layers, creating seamless security across both blockchains.

***

## Reliability and Safeguards

### Automatic Retry

If a Bitcoin transaction fails to broadcast, the Coordinator detects the failure during subsequent checks and rebroadcasts using stored transaction data.

### Idempotent Operations

Each withdrawal generates a unique transaction ID preventing double-spending, even with network-induced retries.

### Distributed Verification

No single Attestor can block or manipulate operations. The threshold system ensures continued operation even with some nodes offline.

***

## Trust and Threat Model

The CBTC system assumes an honest majority of the Attestor network Key trust assumptions:

* A threshold of Attestors must be honest and online for the system to operate
* The Coordinator facilitates but cannot act unilaterally
* BitSafe operates one Attestor node but has no special privileges
* Canton's privacy model ensures transaction details are visible only to involved parties

### What Cannot Happen

* No single party (including BitSafe) can mint CBTC without genuine BTC deposits
* No single party can withdraw BTC without threshold approval
* No front-running or MEV - Canton has no public mempool

***

## Audit Reports

CBTC smart contracts have been audited by **Quantstamp:**

[**View Full Audit Report →**](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html)

***

## Further Reading

* [FROST Whitepaper (ePrint 2020/852)](https://eprint.iacr.org/2020/852)
* [Canton Network Whitepaper](https://www.canton.network/whitepapers)
* [Canton Token Standard Docs](https://docs.dev.sync.global/app_dev/token_standard/index.html#api-references)

***


# Technical Reference

> ⚠️

***

## Token Details

| Property                | Value                                                                                                      |
| ----------------------- | ---------------------------------------------------------------------------------------------------------- |
| **Name**                | CBTC (Canton Bitcoin)                                                                                      |
| **Standard**            | CIP-56 (Canton Instrument Protocol)                                                                        |
| **Backing**             | 1:1 with native BTC                                                                                        |
| **Network**             | Canton Network                                                                                             |
| **Deposit requirement** | Taproot-compatible Bitcoin wallet (P2TR)                                                                   |
| **Transaction limits**  | 0.0001 BTC minimum, 5 BTC maximum by default. Set per account and adjustable on request                    |
| **Confirmations**       | 6 Bitcoin blocks (\~60 minutes)                                                                            |
| **Audit**               | [Quantstamp](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html) |

***

## Network Environments

| Environment | Registry URL                                                                                        | Coordinator URL                                                              | Bitcoin Network |
| ----------- | --------------------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------- | --------------- |
| **Devnet**  | [`https://api.utilities.digitalasset-dev.com`](https://api.utilities.digitalasset-dev.com/)         | [`https://devnet.dlc.link/attestor-2`](https://devnet.dlc.link/attestor-2)   | Bitcoin Testnet |
| **Testnet** | [`https://api.utilities.digitalasset-staging.com`](https://api.utilities.digitalasset-staging.com/) | [`https://testnet.dlc.link/attestor-1`](https://testnet.dlc.link/attestor-1) | Bitcoin Testnet |
| **Mainnet** | [`https://api.utilities.digitalasset.com`](https://api.utilities.digitalasset.com/)                 | [`https://mainnet.dlc.link/attestor-1`](https://mainnet.dlc.link/attestor-1) | Bitcoin Mainnet |

For full Instrument IDs per network, see [Instrument ID Management](https://docs.bitsafe.finance/developers/instrument-id-management).

***

## Canton Network Requirements

To interact with CBTC you need:

1. **Canton participant node** - connected to the target network (devnet/testnet/mainnet)
2. **CBTC DAR files** - installed on your participant. All versions must be installed to access all live contract versions.

* Download: [github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars](https://github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars) (latest DAR: `cbtc-1.2.1`)

1. **OIDC provider** - Keycloak (officially supported) or Auth0 (community example)
2. **Canton CLI** - version 3.3.0+ for DAR upload scripts
3. **Prerequisites for CLI:** `jq`, `curl`, `java` (11+)

### DAR Upload

```bash
git clone https://github.com/DLC-link/cbtc-lib
cd cbtc-lib
# Edit misc/connect.conf to point to your participant
canton run 00_UploadDars.sc -c./misc/connect.conf
```

The upload script is **idempotent** - safe to re-run.

***

## Fee Structure

> ✅ **Confirmed: Mint and burn fees are 0%.** There are no BitSafe fees on CBTC mint or burn operations.

### Canton Transfer Costs

* CBTC transfers on Canton cost approximately **$3-5 per transaction** (network gas, not BitSafe fees)
* Cost varies based on payload size and UTXO count
* Sending CBTC is generally more expensive than sending Canton Coin (CC) due to larger payload

***

## GitHub Repositories

| Repository     | Version      | Description                                         | Link                                                                 |
| -------------- | ------------ | --------------------------------------------------- | -------------------------------------------------------------------- |
| **cbtc-lib**   | `v0.6.4`     | Rust SDK for CBTC operations (mint, burn, transfer) | [GitHub](https://github.com/DLC-link/cbtc-lib)                       |
| **canton-lib** | `v0.6.1`     | Lower-level Canton interaction library              | [GitHub](https://github.com/DLC-link/canton-lib/)                    |
| **CBTC DAR**   | `cbtc-1.2.1` | Daml packages, upload scripts, connect config       | [GitHub](https://github.com/DLC-link/cbtc-lib/tree/v0.6.4/cbtc-dars) |

**Note:** The crate name is `cbtc`. DAR versions and crate versions are numbered independently: `cbtc-lib` v0.6.4 ships DAR `cbtc-1.2.1`.

***

## Transfer Speed

* Canton transfers take **a few seconds each**
* Practical throughput: \~**500 transfers per 10-minute period**
* UTXO limit: **10 UTXOs per party** (Canton recommendation). Exceeding this increases load and fees.

***

## External Links

* [CBTC Technical Documentation (live site)](https://docs.bitsafe.finance/bitsafe-documentation/product-suite/cbtc)
* [Canton Network](https://www.canton.network/)
* [Canton Developer Docs](https://docs.digitalasset.com/)
* [FROST Whitepaper](https://eprint.iacr.org/2020/852)
* [Quantstamp Audit Report](https://certificate.quantstamp.com/full/cbtc/5d0d805e-8cf0-4a39-bf1a-0e94899b3c1c/index.html)
* [Canton Whitepaper](https://www.canton.network/whitepapers)
* [Chainlink Proof of Reserve (CBTC)](https://data.chain.link/)

***


# CBTC Quick Start

> ⚠️ **API Disclaimer.** CBTC APIs have no formal versioning policy today. All endpoints and library interfaces described in this guide are **subject to change**. Breaking changes are communicated via the changelog. This disclaimer will be updated once a formal versioning and stability policy is established.

This step-by-step guide walks you through minting your first CBTC (wrapped Bitcoin) on the Canton Network. You will authenticate with Keycloak, create a deposit account, send BTC to a Taproot address, and receive 1:1 backed CBTC on your Canton participant node. The full process takes about 15 minutes of active work plus \~60 minutes of Bitcoin confirmation time.

> 🎯 **What you will accomplish**
>
> * Authenticate to the Canton Network via Keycloak
> * Create a CBTC deposit account
> * Obtain a Bitcoin deposit address
> * Send BTC and wait for confirmation
> * Verify your CBTC balance
> * Send CBTC to another party (two-phase transfer)

> 🛠️ **Install the SDK first.** Every code example on this page uses the `cbtc-lib` Rust SDK. If you have not installed it yet, start with [SDK Setup and Installation](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) — it covers installing `cbtc-lib` and `canton-lib`, uploading the CBTC DAR files to your participant node, and configuring your environment variables. Come back here once the verification check on that page passes.

***

## Prerequisites for Minting CBTC

Before you begin minting wrapped Bitcoin on Canton, make sure you have the following:

| Requirement                 | Description                                                                                                                                                                                                                                                          |
| --------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| **Canton participant node** | A running Canton participant node connected to the network. See [Canton documentation](https://docs.digitalasset.com/canton) for setup.                                                                                                                              |
| **DA Registry Utility**     | Installed and configured. See [Digital Asset Utilities docs](https://docs.digitalasset.com/utilities/mainnet/index.html).                                                                                                                                            |
| **Keycloak credentials**    | A valid Keycloak host, realm, client ID, username, and password for your environment.                                                                                                                                                                                |
| **Party ID**                | Your Canton Party ID, obtained during onboarding.                                                                                                                                                                                                                    |
| **Minter credential**       | **Required to mint or burn.** Issued to your party by the CBTC registrar as part of onboarding. Request one via <sales@bitsafe.finance>. See [Minting and Burning](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) for how to check and accept it. |
| **Rust toolchain**          | If using cbtc-lib (Rust). Install via [rustup.rs](https://rustup.rs/).                                                                                                                                                                                               |
| **BTC to deposit**          | Real BTC (mainnet) or testnet BTC (testnet). For testnet, you can use the [CBTC Testnet Faucet](https://cbtc-faucet.bitsafe.finance/) to get test CBTC directly. For mainnet, you mint CBTC by depositing real BTC.                                                  |

***

## Choose Your CBTC Environment: Testnet or Mainnet

CBTC is available on three environments. **Start with testnet** for experimentation, then move to mainnet for production. CBTC also exists on Devnet, but minting and withdrawals are not available to external users on Devnet. You can use the faucet to obtain test CBTC for development.

> 🧪 **Testnet vs. Mainnet: what is identical and what differs**
>
> * **Identical:** DAR file, API surface, mint/burn flows, governance model, two-phase transfer mechanics
> * **Differs:** Attestor set (smaller on testnet), confirmation times (may be faster), Instrument IDs (different from mainnet), faucet-only BTC on testnet (no real value)
> * **Mocked or unavailable on testnet:** Real BTC settlement, production Attestor SLAs, mainnet fee structure
> * **Operational note:** Testnet may be reset without notice. Testnet CBTC balances and transaction history may not persist across resets. Do not rely on testnet state for production planning.

### Environment Configuration

| Variable                 | Devnet                                                                                      | Testnet                                                                                             | Mainnet                                                                              |
| ------------------------ | ------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------ |
| `REGISTRY_URL`           | [`https://api.utilities.digitalasset-dev.com`](https://api.utilities.digitalasset-dev.com/) | [`https://api.utilities.digitalasset-staging.com`](https://api.utilities.digitalasset-staging.com/) | [`https://api.utilities.digitalasset.com`](https://api.utilities.digitalasset.com/)  |
| `BITSAFE_API_URL`        | [`https://api.devnet.bitsafe.finance`](https://api.devnet.bitsafe.finance)                  | [`https://api.testnet.bitsafe.finance`](https://api.testnet.bitsafe.finance)                        | [`https://api.mainnet.bitsafe.finance`](https://api.mainnet.bitsafe.finance)         |
| `DECENTRALIZED_PARTY_ID` | `cbtc-network::12202a83c6f4082217c175e29bc53da5f2703ba2675778ab99217a5a881a949203ff`        | `cbtc-network::12201b1741b63e2494e4214cf0bedc3d5a224da53b3bf4d76dba468f8e97eb15508f`                | `cbtc-network::12205af3b949a04776fc48cdcc05a060f6bda2e470632935f375d1049a8546a3b262` |

Set these as environment variables before running any commands:

```bash
export BITSAFE_API_URL="https://api.testnet.bitsafe.finance"
export REGISTRY_URL="<your-registry-url>"
export CANTON_NETWORK="canton-testnet"
export DECENTRALIZED_PARTY_ID="<your-decentralized-party-id>"
export KEYCLOAK_HOST="https://your-keycloak-host"
export KEYCLOAK_REALM="your-realm"
export KEYCLOAK_CLIENT_ID="your-client-id"
export KEYCLOAK_USERNAME="your-username"
export KEYCLOAK_PASSWORD="your-password"
export LEDGER_HOST="https://your-ledger-host"
export PARTY_ID="your-party-id"
```

***

## Step 1: Authenticate with Keycloak

All CBTC operations require a valid Keycloak access token. The `canton-lib` crate provides a helper for this.

### Using cbtc-lib (Rust)

```rust
use keycloak::login::{password, password_url, PasswordParams};

let auth = password(PasswordParams {
 client_id: keycloak_client_id.clone(),
 username: keycloak_username.clone(),
 password: keycloak_password.clone(),
 url: password_url(&keycloak_host, &keycloak_realm),
}).await?;

let access_token = auth.access_token;
```

### Using the Keycloak API directly

```bash
curl -X POST "${KEYCLOAK_HOST}/auth/realms/${KEYCLOAK_REALM}/protocol/openid-connect/token" \
 -H "Content-Type: application/x-www-form-urlencoded" \
 -d "grant_type=password" \
 -d "client_id=${KEYCLOAK_CLIENT_ID}" \
 -d "username=${KEYCLOAK_USERNAME}" \
 -d "password=${KEYCLOAK_PASSWORD}"
```

Save the `access_token` from the response. You will pass it as a Bearer token in all subsequent API calls.

> 💡 **`api_url` in the code examples below** is the BitSafe API base URL — the value you set as `BITSAFE_API_URL` above. It serves the `/cbtc/v1/*` endpoints that back deposit accounts, deposit addresses, and withdrawals.

***

## Step 2: Create a Deposit Account

A deposit account maps your Canton Party ID to a unique Bitcoin deposit address. You only need to create this once; the address can be reused for future deposits.

> ⚠️ **This step requires a Minter credential.** Deposit account creation fails without one. If you have not been issued a Minter credential yet, request one via <sales@bitsafe.finance>. See [Minting and Burning](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) for how to check for and accept your credential.

### Using cbtc-lib

```rust
use cbtc::mint_redeem::{mint, attestor};

// First get account rules from the Attestor
let account_rules = attestor::get_account_contract_rules(&api_url).await?;

let deposit_account = mint::create_deposit_account(mint::CreateDepositAccountParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 account_rules,
 credential_cids: minter_credential_cids.clone(),
}).await?;
```

### Using the Canton API directly

Submit a `CreateDepositAccount` command to the Canton Ledger API v2 endpoint. You can fetch the `CBTCDepositAccountRules` contract from an Attestor's `GET /cbtc/v1/account-contract-rules` endpoint.

```bash
curl -X POST '${LEDGER_HOST}/v2/commands/submit-and-wait-for-transaction-tree' \
 --header 'Authorization: Bearer ${ACCESS_TOKEN}' \
 --data '{
 "commands": [
 {
 "ExerciseCommand": {
 "templateId": "#cbtc:CBTC.DepositAccount:CBTCDepositAccountRules",
 "contractId": "${DA_RULES_CID}",
 "choice": "CBTCDepositAccountRules_CreateDepositAccount",
 "choiceArgument": {
 "owner": "${OWNER_PARTY}"
 }
 }
 }
 ],
 "actAs": [
 "${OWNER_PARTY}"
 ],
 "commandId": "someCommandID",
 "disclosedContracts": [
 {
 "templateId": "#cbtc:CBTC.DepositAccount:CBTCDepositAccountRules",
 "contractId": "${DA_RULES_CID}",
 "createdEventBlob": "${DA_RULES_BLOB}",
 "synchronizerId": ""
 }
 ]
}'
```

{% hint style="info" %}
Note: The submit-and-wait-for-transaction-tree endpoint is deprecated in Canton 3.5 but remains functional. Consider migrating to submit-and-wait-for-transaction for new integrations.
{% endhint %}

> ℹ️ **Ephemeral contract IDs.** `DA_RULES_CID` and `DA_RULES_BLOB` are ephemeral contract IDs. Query them from the Active Contract Service (`POST /v2/state/active-contracts`) at submit time. These IDs change after every consuming exercise.

***

## Step 3: Get Your Bitcoin Deposit Address

Once the deposit account is created, retrieve the Bitcoin address associated with it. This address is derived from the Deposit Account's `id` field (or the `contract_id` if the Deposit Account is new).

### Using cbtc-lib

```rust
let btc_address = mint::get_bitcoin_address(mint::GetBitcoinAddressParams {
 api_url: api_url.clone(),
 account_id: deposit_account.contract_id.clone(),
}).await?;

println!("Send BTC to: {}", btc_address);
```

### Using the BitSafe API directly

Retrieve the deposit address from:

```
GET ${BITSAFE_API_URL}/cbtc/v1/bitcoin-address/{accountId}
```

Use the deposit account's `id` field as `accountId`.

**Important:** This address can be reused indefinitely for future deposits. You can also request additional deposit addresses if needed.

***

## Step 4: Send BTC

Send Bitcoin to the deposit address using any standard Bitcoin wallet or tooling.

> ⚠️ **Deposits are subject to per-account limits.** By default the minimum is **0.0001 BTC** and the maximum is **5 BTC**. A deposit outside that range will not be minted. Limits are set per account and can be adjusted on request - see [Transaction Limits](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) for how to read your account's actual limits at runtime rather than assuming the defaults.

```javascript
Bitcoin address: [your deposit address from Step 3]
```

After sending, you need to wait for **6 Bitcoin block confirmations** before the Attestor network will process the deposit.

***

## Step 5: Wait for Confirmations and Auto-Minting

Once your BTC transaction reaches 6 confirmations:

1. The **Attestor network** detects the confirmed deposit
2. Each Attestor independently verifies the transaction
3. When a threshold of Attestors confirm (via `ConfirmDepositAction` on the CBTC Governance module), CBTC is **automatically minted** to your Canton Party
4. No further action is required from you This process typically takes 60 to 90 minutes, depending on Bitcoin block times.

***

## Step 6: Check Your CBTC Balance

### Using cbtc-lib

```rust
use cbtc::active_contracts;

let holdings = active_contracts::get(active_contracts::Params {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 access_token: access_token.clone(),
}).await?;

println!("CBTC holdings: {} contract(s)", holdings.len());
```

### Using the Canton API directly

Query active contracts filtered by the token holding interface:

```bash
curl -X POST "${LEDGER_HOST}/v2/state/active-contracts" \
 -H "Authorization: Bearer ${ACCESS_TOKEN}" \
 -H "Content-Type: application/json" \
 -d '{
 "filter": {
 "interfaceFilters": [{
 "interfaceId": "#splice-api-token-holding-v1:Splice.Api.Token.HoldingV1:Holding"
 }]
 },
 "activeAtOffset": "${LATEST_OFFSET}"
 }'
```

> 💡 **Filtering required.** This query returns all token holdings, including Canton Coin (CC). To isolate your CBTC balance, you must filter the results client-side by the CBTC `instrumentId`. The `cbtc-lib` library handles this automatically via `active_contracts::get`. There is no single curl that can query and filter for CBTC holdings in one step. The `activeAtOffset` must be set to the actual latest offset from your ledger.

> 💡 **UTXO model.** CBTC uses a UTXO model similar to Bitcoin. Your balance may be spread across multiple holding contracts (soft limit of 10 UTXOs per party per token type). Use the `cbtc::consolidate` module to merge UTXOs, or `cbtc::split` to divide them.

***

## Step 7: Transfer CBTC Between Canton Parties

CBTC transfers use a **two-phase model**: the sender creates an offer, and the receiver accepts it. This ensures both parties explicitly consent to the transfer.

### Phase 1: Create a transfer offer (sender)

```rust
use cbtc::transfer;

transfer::submit(transfer::Params {
 transfer: common::transfer::Transfer {
 sender: sender_party_id.clone(),
 receiver: receiver_party_id.clone(),
 amount: cbtc::DamlDecimal::parse("0.01")?,
 instrument_id: common::transfer::InstrumentId {
 admin: decentralized_party_id.clone(),
 id: "CBTC".to_string(),
 },
 requested_at: chrono::Utc::now().to_rfc3339(),
 execute_before: (chrono::Utc::now() + chrono::Duration::hours(168)).to_rfc3339(),
 input_holding_cids: None,
 meta: None,
 },
 ledger_host: ledger_host.clone(),
 access_token: access_token.clone(),
 registry_url: registry_url.clone(),
 decentralized_party_id: decentralized_party_id.clone(),
}).await?;
```

### Phase 2: Accept the transfer (receiver)

```rust
use cbtc::accept;

accept::submit(accept::Params {
 transfer_offer_contract_id: transfer_contract_id.clone(),
 receiver_party: receiver_party_id.clone(),
 ledger_host: ledger_host.clone(),
 access_token: receiver_access_token.clone(),
 registry_url: registry_url.clone(),
 decentralized_party_id: decentralized_party_id.clone(),
}).await?;
```

> ℹ️ **No curl example for transfers.** The raw API transfer flow requires 5-6 sequential API calls with contract disclosures and is too complex to represent as a single curl example. Use `cbtc-lib` for transfers, or refer to the [Canton Utility docs](https://docs.digitalasset.com/utilities/mainnet/index.html) for the full API sequence.

> 💡 **This is a free-of-payment (FOP) transfer.** CBTC moves in one direction with nothing exchanged in return. If you need **delivery-versus-payment** — where CBTC only moves if a second leg moves atomically with it — use the `cbtc::allocation` module instead. See [DvP Settlement Using Allocations](https://docs.bitsafe.finance/developers/integration-guides) in the Integration Guides.

***

## Redeem CBTC: Convert Wrapped Bitcoin Back to BTC

To convert CBTC back to BTC (this also requires a Minter credential):

1. **Create a withdraw account** specifying your Bitcoin destination address using the `cbtc::mint_redeem::redeem` module
2. **Submit the withdrawal** which burns CBTC on Canton
3. The **Attestor network** detects the burn and constructs a Bitcoin transaction
4. Attestors sign the transaction via threshold signing (FROST)
5. The BTC transaction is broadcast to the Bitcoin network

### Using cbtc-lib

```rust
use cbtc::mint_redeem::redeem;

// 1. Create a withdraw account with your BTC destination address
let withdraw_account = redeem::create_withdraw_account(redeem::CreateWithdrawAccountParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 account_rules_contract_id: rules.wa_rules.contract_id.clone(),
 account_rules_template_id: rules.wa_rules.template_id.clone(),
 account_rules_created_event_blob: rules.wa_rules.created_event_blob.clone(),
 destination_btc_address: btc_destination_address.clone(),
 credential_cids: minter_credential_cids.clone(),
}).await?;

// 2. Submit the withdrawal (burns CBTC, Attestors process BTC payout)
let updated_account = redeem::submit_withdraw(redeem::SubmitWithdrawParams {
 ledger_host: ledger_host.clone(),
 party: party_id.clone(),
 user_name: username.clone(),
 access_token: access_token.clone(),
 api_url: api_url.clone(),
 withdraw_account_contract_id: withdraw_account.contract_id.clone(),
 amount: cbtc::DamlDecimal::parse("0.001")?,
 holding_contract_ids: holding_ids,
 credential_cids: Some(minter_credential_cids.clone()),
}).await?;

println!("Pending balance: {}", updated_account.pending_balance);
```

### Using the Canton API directly

Submit a `CBTCWithdrawAccount_Withdraw` command. You can get the correct `extraArgs` and contract disclosures from an Attestor's `GET /cbtc/v1/token-standard-contracts` endpoint. The `contractIds`, `templateIds`, and `blobs` in this example are for illustration only:

```bash
curl -X POST '${LEDGER_HOST}/v2/commands/submit-and-wait-for-transaction-tree' \
 --header 'Authorization: Bearer ${ACCESS_TOKEN}' \
 --data '{
 "commands": [
 {
 "ExerciseCommand": {
 "templateId": "#cbtc:CBTC.WithdrawAccount:CBTCWithdrawAccount",
 "contractId": "${WA_CID}",
 "choice": "CBTCWithdrawAccount_Withdraw",
 "choiceArgument": {
 "amount": "${AMOUNT}",
 "tokens": [
 "${INPUT_HOLDING}"
 ],
 "burnMintFactoryCid": "${ALLOCATION_FACTORY_CID}",
 "extraArgs": {
 "context": {
 "values": {
 "utility.digitalasset.com/instrument-configuration": {
 "tag": "AV_ContractId",
 "value": "00da61fcfa2d9b358c606f040a1d635fbabe4265d33908744a148a80be0dcdc383ca111220e86787467ef7be665f68b813a30de6b0480955dcb514ef29832720618375dee5"
 },
 "utility.digitalasset.com/app-reward-configuration": {
 "tag": "AV_ContractId",
 "value": "00bee23612f3c82dd6091e64ffde81cb535e7b446d7ebdf6d91329502c6023d1cdca1112209569dade5e20bf97f963882f6387293034a82f716d2b0df28820a82048f5f86c"
 },
 "utility.digitalasset.com/featured-app-right": {
 "tag": "AV_ContractId",
 "value": "001c6e92181f8de9e4d15956e33f90db3085c518747de627134b6850459bf3662fca111220ee87bf1e3b05ed4d3f8a6c336290660f23409cb8d11a028e1073137eac8f78bf"
 },
 "utility.digitalasset.com/issuer-credentials": {
 "tag": "AV_List",
 "value": [
 {
 "tag": "AV_ContractId",
 "value": "0058feffeeaa48cc5526c723c4877af4f6abe3c76131c54ba0d63c6da299f8681bca111220b7032514b6b448d75ea6d9eefe01f0a345504e897a5f2e72fabf974322b20b07"
 }
 ]
 }
 }
 },
 "meta": {
 "values": {
 "splice.lfdecentralizedtrust.org/reason": "CBTC Burn"
 }
 }
 }
 }
 }
 }
 ],
 "actAs": [
 "${OWNER_PARTY}"
 ],
 "commandId": "someCommandId",
 "disclosedContracts": [
 {
 "templateId": "82798df018301852704f210b97adaabf76d3ecd37d889e1bf96b5f31a20eea34:Utility.Registry.App.V0.Service.AllocationFactory:AllocationFactory",
 "contractId": "00d58a5f061f086b3c4b405b57ca08f4cefcb7f3a27a26089be6388eb62ee619a8ca1112200991d565daa04ca691901bc04238a8655e2c068039130e4c00027eac2675d9f4",
 "createdEventBlob": "CgMyLjEShwYKRQDVil8GHwhrPEtAW1fKCPTO/LfzonomCJvmOI62LuYZqMoREiAJkdVl2qBMppGQG8BCOKhlXiwGgDkTDkwAAn6sJnXZ9BIXdXRpbGl0eS1yZWdpc3RyeS1hcHAtdjAajQEKQDgyNzk4ZGYwMTgzMDE4NTI3MDRmMjEwYjk3YWRhYWJmNzZkM2VjZDM3ZDg4OWUxYmY5NmI1ZjMxYTIwZWVhMzQSB1V0aWxpdHkSCFJlZ2lzdHJ5EgNBcHASAlYwEgdTZXJ2aWNlEhFBbGxvY2F0aW9uRmFjdG9yeRoRQWxsb2NhdGlvbkZhY3RvcnkioQJqngIKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmClYKVDpSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgpsCmo6aGF1dGgwXzAwN2M2NWY4NTdmMWMzZDU5OWNiNmRmNzM3NzU6OjEyMjBkMmQ3MzJkMDQyYzI4MWNlZTgwZjQ4M2FiODBmM2NiYWE0NzgyODYwZWQ1ZjRkYzIyOGFiMDNkZWRkMmVlOGY5KlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmMmhhdXRoMF8wMDdjNjVmODU3ZjFjM2Q1OTljYjZkZjczNzc1OjoxMjIwZDJkNzMyZDA0MmMyODFjZWU4MGY0ODNhYjgwZjNjYmFhNDc4Mjg2MGVkNWY0ZGMyMjhhYjAzZGVkZDJlZThmOTlubOVh5DkGAEIqCiYKJAgBEiCdDhxHJbSFz7Snbvg8xLkPDPvaP3wl+HzTfq2LxHAGmRAe",
 "synchronizerId": ""
 },
 {
 "templateId": "3ca1343ab26b453d38c8adb70dca5f1ead8440c42b59b68f070786955cbf9ec1:Splice.Amulet:FeaturedAppRight",
 "contractId": "001c6e92181f8de9e4d15956e33f90db3085c518747de627134b6850459bf3662fca111220ee87bf1e3b05ed4d3f8a6c336290660f23409cb8d11a028e1073137eac8f78bf",
 "createdEventBlob": "CgMyLjESvQQKRQAcbpIYH43p5NFZVuM/kNswhcUYdH3mJxNLaFBFm/NmL8oREiDuh78eOwXtTT+KbDNikGYPI0CcuNEaAo4QcxN+rI94vxINc3BsaWNlLWFtdWxldBpkCkAzY2ExMzQzYWIyNmI0NTNkMzhjOGFkYjcwZGNhNWYxZWFkODQ0MGM0MmI1OWI2OGYwNzA3ODY5NTVjYmY5ZWMxEgZTcGxpY2USBkFtdWxldBoQRmVhdHVyZWRBcHBSaWdodCKqAWqnAQpNCks6SURTTzo6MTIyMGJlNThjMjllNjVkZTQwYmYyNzNiZTFkYzJiMjY2ZDQzYTlhMDAyZWE1YjE4OTU1YWVlZjdhYWM4ODFiYjQ3MWEKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmKklEU086OjEyMjBiZTU4YzI5ZTY1ZGU0MGJmMjczYmUxZGMyYjI2NmQ0M2E5YTAwMmVhNWIxODk1NWFlZWY3YWFjODgxYmI0NzFhMlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmOVDK9pNvQQYAQioKJgokCAESIOo7ddJGewmnI6M13zqEh5d8VRVxWJ73gao2y0uty955EB4=",
 "synchronizerId": ""
 },
 {
 "templateId": "ed73d5b9ab717333f3dbd122de7be3156f8bf2614a67360c3dd61fc0135133fa:Utility.Registry.V0.Configuration.Instrument:InstrumentConfiguration",
 "contractId": "00da61fcfa2d9b358c606f040a1d635fbabe4265d33908744a148a80be0dcdc383ca111220e86787467ef7be665f68b813a30de6b0480955dcb514ef29832720618375dee5",
 "createdEventBlob": "CgMyLjESnwkKRQDaYfz6LZs1jGBvBAodY1+6vkJl0zkIdEoUioC+Dc3Dg8oREiDoZ4dGfve+Zl9ouBOjDeawSAlV3LUU7ymDJyBhg3Xe5RITdXRpbGl0eS1yZWdpc3RyeS12MBqNAQpAZWQ3M2Q1YjlhYjcxNzMzM2YzZGJkMTIyZGU3YmUzMTU2ZjhiZjI2MTRhNjczNjBjM2RkNjFmYzAxMzUxMzNmYRIHVXRpbGl0eRIIUmVnaXN0cnkSAlYwEg1Db25maWd1cmF0aW9uEgpJbnN0cnVtZW50GhdJbnN0cnVtZW50Q29uZmlndXJhdGlvbiK9BWq6BQpsCmo6aGF1dGgwXzAwN2M2NWY4NTdmMWMzZDU5OWNiNmRmNzM3NzU6OjEyMjBkMmQ3MzJkMDQyYzI4MWNlZTgwZjQ4M2FiODBmM2NiYWE0NzgyODYwZWQ1ZjRkYzIyOGFiMDNkZWRkMmVlOGY5ClYKVDpSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKhAEKgQFqfwpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKCAoGQgRDQlRDChsKGUIXUmVnaXN0cmFySW50ZXJuYWxTY2hlbWUKigEKhwFahAEKgQFqfwpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKCAoGQgRDQlRDChsKGUIXUmVnaXN0cmFySW50ZXJuYWxTY2hlbWUKBAoCWgAKBAoCWgAKegp4UnYKdFpyCnBqbgpaClg6VmNidGMtYmVuZWZpY2lhcnk6OjEyMjBmYTg1NDNkYjZjNjZmZTNhNTViMWYxODBjOGRmYzdmODc2MjY1Yzc2Njg0ZmJjMWQzNWQ4OWUwMmM4YWFmZThlChAKDjIMMS4wMDAwMDAwMDAwKlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmMmhhdXRoMF8wMDdjNjVmODU3ZjFjM2Q1OTljYjZkZjczNzc1OjoxMjIwZDJkNzMyZDA0MmMyODFjZWU4MGY0ODNhYjgwZjNjYmFhNDc4Mjg2MGVkNWY0ZGMyMjhhYjAzZGVkZDJlZThmOTnz2t5E5kEGAEIqCiYKJAgBEiAb19AdEjIoV/7xtMY8A2/BkXnnQHGPcCNC0UEu/b5/YxAe",
 "synchronizerId": ""
 },
 {
 "templateId": "77df4e7b980c12de438d7b052141a762215fae790d81f71179c8fb534beb68f7:Utility.Credential.V0.Credential:Credential",
 "contractId": "0058feffeeaa48cc5526c723c4877af4f6abe3c76131c54ba0d63c6da299f8681bca111220b7032514b6b448d75ea6d9eefe01f0a345504e897a5f2e72fabf974322b20b07",
 "createdEventBlob": "CgMyLjESjQgKRQBY/v/uqkjMVSbHI8SHevT2q+PHYTHFS6DWPG2imfhoG8oREiC3AyUUtrRI116m2e7+AfCjRVBOiXpfLnL6v5dDIrILBxIVdXRpbGl0eS1jcmVkZW50aWFsLXYwGnMKQDc3ZGY0ZTdiOTgwYzEyZGU0MzhkN2IwNTIxNDFhNzYyMjE1ZmFlNzkwZDgxZjcxMTc5YzhmYjUzNGJlYjY4ZjcSB1V0aWxpdHkSCkNyZWRlbnRpYWwSAlYwEgpDcmVkZW50aWFsGgpDcmVkZW50aWFsIuwDaukDCloKWDpWaUJUQy12YWxpZGF0b3ItMTo6MTIyMGZhODU0M2RiNmM2NmZlM2E1NWIxZjE4MGM4ZGZjN2Y4NzYyNjVjNzY2ODRmYmMxZDM1ZDg5ZTAyYzhhYWZlOGUKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmChIKEEIOY2J0Yy1wcm92LWhhY2sKDgoMQgpXb3JrYXJvdW5kCgQKAlIACgQKAlIACoQBCoEBWn8KfWp7ClYKVEJSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgoTChFCD2hhc1JlZ2lzdHJ5Um9sZQoMCgpCCFByb3ZpZGVyCnwKemp4CnYKdGJyCnAKajpoYXV0aDBfMDA3YzY1Zjg1N2YxYzNkNTk5Y2I2ZGY3Mzc3NTo6MTIyMGQyZDczMmQwNDJjMjgxY2VlODBmNDgzYWI4MGYzY2JhYTQ3ODI4NjBlZDVmNGRjMjI4YWIwM2RlZGQyZWU4ZjkSAgoAKlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmKlZpQlRDLXZhbGlkYXRvci0xOjoxMjIwZmE4NTQzZGI2YzY2ZmUzYTU1YjFmMTgwYzhkZmM3Zjg3NjI2NWM3NjY4NGZiYzFkMzVkODllMDJjOGFhZmU4ZTJoYXV0aDBfMDA3YzY1Zjg1N2YxYzNkNTk5Y2I2ZGY3Mzc3NTo6MTIyMGQyZDczMmQwNDJjMjgxY2VlODBmNDgzYWI4MGYzY2JhYTQ3ODI4NjBlZDVmNGRjMjI4YWIwM2RlZGQyZWU4Zjk5iBIJ/7RABgBCKgomCiQIARIgwrTBnrlaL0STx5Hh0v7BEmbbCERCZDgwJWqqcljhQZ0QHg==",
 "synchronizerId": ""
 }
 ]
}'
```

***

## Additional Operations

The `cbtc-lib` library provides several utility modules for managing your CBTC holdings:

| Module                   | Purpose                                           |
| ------------------------ | ------------------------------------------------- |
| `cbtc::batch`            | Batch operations for sending CBTC from a CSV file |
| `cbtc::distribute`       | Distribute CBTC across multiple parties           |
| `cbtc::consolidate`      | Merge multiple UTXO holdings into fewer contracts |
| `cbtc::split`            | Split a single holding into multiple UTXOs        |
| `cbtc::active_contracts` | Query your current CBTC holdings                  |

***

## Troubleshooting

<details>

<summary>My deposit has not been minted after 90 minutes</summary>

* Verify the BTC transaction has at least 6 confirmations on a block explorer
* Confirm you sent to the correct deposit address (from Step 3)
* Check that your Canton participant node is connected and syncing
* Escalation: contact <support@bitsafe.finance>

</details>

<details>

<summary>Transfer offer is not appearing for the receiver</summary>

* The receiver must be registered in the DA Registry with a valid credential
* Confirm the receiver's Party ID is correct
* Check that both parties are connected to the same Canton sync domain

</details>

<details>

<summary>"Insufficient holdings" error when sending</summary>

* CBTC uses a UTXO model. You may need to consolidate holdings first using `cbtc::consolidate`
* Check your balance with `cbtc::active_contracts` to verify available amounts

</details>

<details>

<summary>Authentication token expired</summary>

* Keycloak tokens have a limited lifetime. Re-authenticate using Step 1 before retrying the operation

</details>

***

## Next Steps

* [**CBTC Minting and Burning**](https://docs.bitsafe.finance/developers/cbtc-minting-and-burning) - The same mint and burn flows in more depth, with error handling and recovery patterns for production
* [**API Reference**](https://docs.bitsafe.finance/developers/cbtc-api-reference) - Canton Ledger API endpoints, instrument IDs, rate limits, and error codes
* [**SDK Setup and Installation**](https://docs.bitsafe.finance/developers/sdk-setup-and-installation) - Full `cbtc-lib` and `canton-lib` module reference
* [**Authentication Guide**](https://docs.bitsafe.finance/developers/cbtc-authentication) - Detailed Keycloak setup and an Auth0 community example
* [**Integration Guides**](https://docs.bitsafe.finance/developers/integration-guides) - Patterns for DeFi protocols, wallets, custody, and trading systems
* [**Withdraw via curl**](/developers/cbtc-quick-start/withdraw-curl) - The raw API withdrawal sequence, without the SDK

***

> 📧 **Need help?** Reach out to <support@bitsafe.finance>


# Withdraw curl

You can get the correct extraArgs and contract disclosures from the BitSafe API's `/cbtc/v1/token-standard-contracts` endpoint. So the contractIds, templateIds, and blobs in this example are just for example:

```bash
curl -X POST '${LEDGER_HOST}/v2/commands/submit-and-wait-for-transaction-tree' \
 --header 'Authorization: Bearer ${ACCESS_TOKEN}' \
 --data '{
 "commands": [
 {
 "ExerciseCommand": {
 "templateId": "#cbtc:CBTC.WithdrawAccount:CBTCWithdrawAccount",
 "contractId": "${WA_CID}",
 "choice": "CBTCWithdrawAccount_Withdraw",
 "choiceArgument": {
 "amount": "${AMOUNT}",
 "tokens": [
 "${INPUT_HOLDING}"
 ],
 "burnMintFactoryCid": "${ALLOCATION_FACTORY_CID}",
 "extraArgs": {
 "context": {
 "values": {
 "utility.digitalasset.com/instrument-configuration": {
 "tag": "AV_ContractId",
 "value": "00da61fcfa2d9b358c606f040a1d635fbabe4265d33908744a148a80be0dcdc383ca111220e86787467ef7be665f68b813a30de6b0480955dcb514ef29832720618375dee5"
 },
 "utility.digitalasset.com/app-reward-configuration": {
 "tag": "AV_ContractId",
 "value": "00bee23612f3c82dd6091e64ffde81cb535e7b446d7ebdf6d91329502c6023d1cdca1112209569dade5e20bf97f963882f6387293034a82f716d2b0df28820a82048f5f86c"
 },
 "utility.digitalasset.com/featured-app-right": {
 "tag": "AV_ContractId",
 "value": "001c6e92181f8de9e4d15956e33f90db3085c518747de627134b6850459bf3662fca111220ee87bf1e3b05ed4d3f8a6c336290660f23409cb8d11a028e1073137eac8f78bf"
 },
 "utility.digitalasset.com/issuer-credentials": {
 "tag": "AV_List",
 "value": [
 {
 "tag": "AV_ContractId",
 "value": "0058feffeeaa48cc5526c723c4877af4f6abe3c76131c54ba0d63c6da299f8681bca111220b7032514b6b448d75ea6d9eefe01f0a345504e897a5f2e72fabf974322b20b07"
 }
 ]
 }
 }
 },
 "meta": {
 "values": {
 "splice.lfdecentralizedtrust.org/reason": "CBTC Burn"
 }
 }
 }
 }
 }
 }
 ],
 "actAs": [
 "${OWNER_PARTY}"
 ],
 "commandId": "someCommandId",
 "disclosedContracts": [
 {
 "templateId": "82798df018301852704f210b97adaabf76d3ecd37d889e1bf96b5f31a20eea34:Utility.Registry.App.V0.Service.AllocationFactory:AllocationFactory",
 "contractId": "00d58a5f061f086b3c4b405b57ca08f4cefcb7f3a27a26089be6388eb62ee619a8ca1112200991d565daa04ca691901bc04238a8655e2c068039130e4c00027eac2675d9f4",
 "createdEventBlob": "CgMyLjEShwYKRQDVil8GHwhrPEtAW1fKCPTO/LfzonomCJvmOI62LuYZqMoREiAJkdVl2qBMppGQG8BCOKhlXiwGgDkTDkwAAn6sJnXZ9BIXdXRpbGl0eS1yZWdpc3RyeS1hcHAtdjAajQEKQDgyNzk4ZGYwMTgzMDE4NTI3MDRmMjEwYjk3YWRhYWJmNzZkM2VjZDM3ZDg4OWUxYmY5NmI1ZjMxYTIwZWVhMzQSB1V0aWxpdHkSCFJlZ2lzdHJ5EgNBcHASAlYwEgdTZXJ2aWNlEhFBbGxvY2F0aW9uRmFjdG9yeRoRQWxsb2NhdGlvbkZhY3RvcnkioQJqngIKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmClYKVDpSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgpsCmo6aGF1dGgwXzAwN2M2NWY4NTdmMWMzZDU5OWNiNmRmNzM3NzU6OjEyMjBkMmQ3MzJkMDQyYzI4MWNlZTgwZjQ4M2FiODBmM2NiYWE0NzgyODYwZWQ1ZjRkYzIyOGFiMDNkZWRkMmVlOGY5KlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmMmhhdXRoMF8wMDdjNjVmODU3ZjFjM2Q1OTljYjZkZjczNzc1OjoxMjIwZDJkNzMyZDA0MmMyODFjZWU4MGY0ODNhYjgwZjNjYmFhNDc4Mjg2MGVkNWY0ZGMyMjhhYjAzZGVkZDJlZThmOTlubOVh5DkGAEIqCiYKJAgBEiCdDhxHJbSFz7Snbvg8xLkPDPvaP3wl+HzTfq2LxHAGmRAe",
 "synchronizerId": ""
 },
 {
 "templateId": "3ca1343ab26b453d38c8adb70dca5f1ead8440c42b59b68f070786955cbf9ec1:Splice.Amulet:FeaturedAppRight",
 "contractId": "001c6e92181f8de9e4d15956e33f90db3085c518747de627134b6850459bf3662fca111220ee87bf1e3b05ed4d3f8a6c336290660f23409cb8d11a028e1073137eac8f78bf",
 "createdEventBlob": "CgMyLjESvQQKRQAcbpIYH43p5NFZVuM/kNswhcUYdH3mJxNLaFBFm/NmL8oREiDuh78eOwXtTT+KbDNikGYPI0CcuNEaAo4QcxN+rI94vxINc3BsaWNlLWFtdWxldBpkCkAzY2ExMzQzYWIyNmI0NTNkMzhjOGFkYjcwZGNhNWYxZWFkODQ0MGM0MmI1OWI2OGYwNzA3ODY5NTVjYmY5ZWMxEgZTcGxpY2USBkFtdWxldBoQRmVhdHVyZWRBcHBSaWdodCKqAWqnAQpNCks6SURTTzo6MTIyMGJlNThjMjllNjVkZTQwYmYyNzNiZTFkYzJiMjY2ZDQzYTlhMDAyZWE1YjE4OTU1YWVlZjdhYWM4ODFiYjQ3MWEKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmKklEU086OjEyMjBiZTU4YzI5ZTY1ZGU0MGJmMjczYmUxZGMyYjI2NmQ0M2E5YTAwMmVhNWIxODk1NWFlZWY3YWFjODgxYmI0NzFhMlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmOVDK9pNvQQYAQioKJgokCAESIOo7ddJGewmnI6M13zqEh5d8VRVxWJ73gao2y0uty955EB4=",
 "synchronizerId": ""
 },
 {
 "templateId": "ed73d5b9ab717333f3dbd122de7be3156f8bf2614a67360c3dd61fc0135133fa:Utility.Registry.V0.Configuration.Instrument:InstrumentConfiguration",
 "contractId": "00da61fcfa2d9b358c606f040a1d635fbabe4265d33908744a148a80be0dcdc383ca111220e86787467ef7be665f68b813a30de6b0480955dcb514ef29832720618375dee5",
 "createdEventBlob": "CgMyLjESnwkKRQDaYfz6LZs1jGBvBAodY1+6vkJl0zkIdEoUioC+Dc3Dg8oREiDoZ4dGfve+Zl9ouBOjDeawSAlV3LUU7ymDJyBhg3Xe5RITdXRpbGl0eS1yZWdpc3RyeS12MBqNAQpAZWQ3M2Q1YjlhYjcxNzMzM2YzZGJkMTIyZGU3YmUzMTU2ZjhiZjI2MTRhNjczNjBjM2RkNjFmYzAxMzUxMzNmYRIHVXRpbGl0eRIIUmVnaXN0cnkSAlYwEg1Db25maWd1cmF0aW9uEgpJbnN0cnVtZW50GhdJbnN0cnVtZW50Q29uZmlndXJhdGlvbiK9BWq6BQpsCmo6aGF1dGgwXzAwN2M2NWY4NTdmMWMzZDU5OWNiNmRmNzM3NzU6OjEyMjBkMmQ3MzJkMDQyYzI4MWNlZTgwZjQ4M2FiODBmM2NiYWE0NzgyODYwZWQ1ZjRkYzIyOGFiMDNkZWRkMmVlOGY5ClYKVDpSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKhAEKgQFqfwpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKCAoGQgRDQlRDChsKGUIXUmVnaXN0cmFySW50ZXJuYWxTY2hlbWUKigEKhwFahAEKgQFqfwpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYKCAoGQgRDQlRDChsKGUIXUmVnaXN0cmFySW50ZXJuYWxTY2hlbWUKBAoCWgAKBAoCWgAKegp4UnYKdFpyCnBqbgpaClg6VmNidGMtYmVuZWZpY2lhcnk6OjEyMjBmYTg1NDNkYjZjNjZmZTNhNTViMWYxODBjOGRmYzdmODc2MjY1Yzc2Njg0ZmJjMWQzNWQ4OWUwMmM4YWFmZThlChAKDjIMMS4wMDAwMDAwMDAwKlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmMmhhdXRoMF8wMDdjNjVmODU3ZjFjM2Q1OTljYjZkZjczNzc1OjoxMjIwZDJkNzMyZDA0MmMyODFjZWU4MGY0ODNhYjgwZjNjYmFhNDc4Mjg2MGVkNWY0ZGMyMjhhYjAzZGVkZDJlZThmOTnz2t5E5kEGAEIqCiYKJAgBEiAb19AdEjIoV/7xtMY8A2/BkXnnQHGPcCNC0UEu/b5/YxAe",
 "synchronizerId": ""
 },
 {
 "templateId": "77df4e7b980c12de438d7b052141a762215fae790d81f71179c8fb534beb68f7:Utility.Credential.V0.Credential:Credential",
 "contractId": "0058feffeeaa48cc5526c723c4877af4f6abe3c76131c54ba0d63c6da299f8681bca111220b7032514b6b448d75ea6d9eefe01f0a345504e897a5f2e72fabf974322b20b07",
 "createdEventBlob": "CgMyLjESjQgKRQBY/v/uqkjMVSbHI8SHevT2q+PHYTHFS6DWPG2imfhoG8oREiC3AyUUtrRI116m2e7+AfCjRVBOiXpfLnL6v5dDIrILBxIVdXRpbGl0eS1jcmVkZW50aWFsLXYwGnMKQDc3ZGY0ZTdiOTgwYzEyZGU0MzhkN2IwNTIxNDFhNzYyMjE1ZmFlNzkwZDgxZjcxMTc5YzhmYjUzNGJlYjY4ZjcSB1V0aWxpdHkSCkNyZWRlbnRpYWwSAlYwEgpDcmVkZW50aWFsGgpDcmVkZW50aWFsIuwDaukDCloKWDpWaUJUQy12YWxpZGF0b3ItMTo6MTIyMGZhODU0M2RiNmM2NmZlM2E1NWIxZjE4MGM4ZGZjN2Y4NzYyNjVjNzY2ODRmYmMxZDM1ZDg5ZTAyYzhhYWZlOGUKVgpUOlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmChIKEEIOY2J0Yy1wcm92LWhhY2sKDgoMQgpXb3JrYXJvdW5kCgQKAlIACgQKAlIACoQBCoEBWn8KfWp7ClYKVEJSY2J0Yy1uZXR3b3JrOjoxMjIwMmE4M2M2ZjQwODIyMTdjMTc1ZTI5YmM1M2RhNWYyNzAzYmEyNjc1Nzc4YWI5OTIxN2E1YTg4MWE5NDkyMDNmZgoTChFCD2hhc1JlZ2lzdHJ5Um9sZQoMCgpCCFByb3ZpZGVyCnwKemp4CnYKdGJyCnAKajpoYXV0aDBfMDA3YzY1Zjg1N2YxYzNkNTk5Y2I2ZGY3Mzc3NTo6MTIyMGQyZDczMmQwNDJjMjgxY2VlODBmNDgzYWI4MGYzY2JhYTQ3ODI4NjBlZDVmNGRjMjI4YWIwM2RlZGQyZWU4ZjkSAgoAKlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmKlZpQlRDLXZhbGlkYXRvci0xOjoxMjIwZmE4NTQzZGI2YzY2ZmUzYTU1YjFmMTgwYzhkZmM3Zjg3NjI2NWM3NjY4NGZiYzFkMzVkODllMDJjOGFhZmU4ZTJoYXV0aDBfMDA3YzY1Zjg1N2YxYzNkNTk5Y2I2ZGY3Mzc3NTo6MTIyMGQyZDczMmQwNDJjMjgxY2VlODBmNDgzYWI4MGYzY2JhYTQ3ODI4NjBlZDVmNGRjMjI4YWIwM2RlZGQyZWU4Zjk5iBIJ/7RABgBCKgomCiQIARIgwrTBnrlaL0STx5Hh0v7BEmbbCERCZDgwJWqqcljhQZ0QHg==",
 "synchronizerId": ""
 },
 {
 "templateId": "ed73d5b9ab717333f3dbd122de7be3156f8bf2614a67360c3dd61fc0135133fa:Utility.Registry.V0.Configuration.AppReward:AppRewardConfiguration",
 "contractId": "00bee23612f3c82dd6091e64ffde81cb535e7b446d7ebdf6d91329502c6023d1cdca1112209569dade5e20bf97f963882f6387293034a82f716d2b0df28820a82048f5f86c",
 "createdEventBlob": "CgMyLjESigcKRQC+4jYS88gt1gkeZP/egctTXntEbX699tkTKVAsYCPRzcoREiCVadreXiC/l/ljiC9jhykwNKgvcW0rDfKIIKggSPX4bBITdXRpbGl0eS1yZWdpc3RyeS12MBqLAQpAZWQ3M2Q1YjlhYjcxNzMzM2YzZGJkMTIyZGU3YmUzMTU2ZjhiZjI2MTRhNjczNjBjM2RkNjFmYzAxMzUxMzNmYRIHVXRpbGl0eRIIUmVnaXN0cnkSAlYwEg1Db25maWd1cmF0aW9uEglBcHBSZXdhcmQaFkFwcFJld2FyZENvbmZpZ3VyYXRpb24iqgNqpwMKbApqOmhhdXRoMF8wMDdjNjVmODU3ZjFjM2Q1OTljYjZkZjczNzc1OjoxMjIwZDJkNzMyZDA0MmMyODFjZWU4MGY0ODNhYjgwZjNjYmFhNDc4Mjg2MGVkNWY0ZGMyMjhhYjAzZGVkZDJlZThmOQpWClQ6UmNidGMtbmV0d29yazo6MTIyMDJhODNjNmY0MDgyMjE3YzE3NWUyOWJjNTNkYTVmMjcwM2JhMjY3NTc3OGFiOTkyMTdhNWE4ODFhOTQ5MjAzZmYK3gEK2wFq2AEKTQpLOklEU086OjEyMjBiZTU4YzI5ZTY1ZGU0MGJmMjczYmUxZGMyYjI2NmQ0M2E5YTAwMmVhNWIxODk1NWFlZWY3YWFjODgxYmI0NzFhCoYBCoMBaoABCmwKajpoYXV0aDBfMDA3YzY1Zjg1N2YxYzNkNTk5Y2I2ZGY3Mzc3NTo6MTIyMGQyZDczMmQwNDJjMjgxY2VlODBmNDgzYWI4MGYzY2JhYTQ3ODI4NjBlZDVmNGRjMjI4YWIwM2RlZGQyZWU4ZjkKEAoOMgwwLjIwMDAwMDAwMDAqaGF1dGgwXzAwN2M2NWY4NTdmMWMzZDU5OWNiNmRmNzM3NzU6OjEyMjBkMmQ3MzJkMDQyYzI4MWNlZTgwZjQ4M2FiODBmM2NiYWE0NzgyODYwZWQ1ZjRkYzIyOGFiMDNkZWRkMmVlOGY5MlJjYnRjLW5ldHdvcms6OjEyMjAyYTgzYzZmNDA4MjIxN2MxNzVlMjliYzUzZGE1ZjI3MDNiYTI2NzU3NzhhYjk5MjE3YTVhODgxYTk0OTIwM2ZmOTNRkpGtQQYAQioKJgokCAESIEkSmOztxETzHu7k7YoYrhYmnA4xZxW6uqMAl1xkvmiOEB4=",
 "synchronizerId": ""
 }
 ]
}'
```


