Token lifecycle
Visual flowcharts showing the complete token lifecycle from creation through minting, transfers, and burns with required API calls and permissions.
This guide visualizes the token lifecycle through flowcharts for each major operation. Use these diagrams to understand the sequence of API calls, required roles, and decision points when building automated workflows.

Create token operation
Creating a token deploys a new smart contract and configures its initial parameters.
Prerequisites:
- API key for authentication
tokenManagersystem role- Registered identity for your wallet
Required inputs:
- Common:
type,name,symbol,decimals,countryCode,initialModulePairs,walletVerification - Bond-specific:
faceValue,maturityDate,denominationAsset - Stablecoin-specific:
priceCurrency,basePrice - Fund-specific:
priceCurrency,basePrice
Auto-granted roles:
When you create a token, you automatically receive:
admin– Allows granting other roles on this tokengovernance– Allows configuring compliance modules and token parameters
Next steps:
- Grant
supplyManagementrole (for minting) - Grant
emergencyrole (for unpausing) - Unpause the token
- Add collateral (stablecoins only)
- Mint initial supply
Example guides:
Mint tokens operation
Minting increases the token supply and sends tokens to specified recipients.
Prerequisites:
- API key for authentication
supplyManagementtoken role- Token must be unpaused (requires
emergencyrole) - Recipients must have registered identities
- For stablecoins: sufficient collateral must be added (requires trusted issuer status)
Required inputs:
tokenAddress– Contract address from token creationrecipients– Array of wallet addressesamounts– Array of amounts in smallest unit (BigInt)walletVerification– PINCODE verification
Validation checks:
- Token is unpaused
- Caller has
supplyManagementrole - Minting does not exceed cap (if set)
- Recipients have registered identities
- Stablecoins: sufficient collateral exists
Amount calculation:
All tokens use 18 decimals. To mint 100 tokens:
import { from } from "dnum";
const amount = from("100", 18); // 100 tokensExample:
import { from } from "dnum";
await client.token.mint({
tokenAddress: "0xABCD...",
recipients: ["0x1234...", "0x5678..."],
amounts: [from("100", 18), from("200", 18)],
walletVerification: {
verificationType: "PINCODE",
secretVerificationCode: "123456",
},
});Burn tokens operation
Burning permanently reduces the token supply by destroying tokens from the caller's balance.
Prerequisites:
- API key for authentication
supplyManagementtoken role- Sufficient token balance to burn
Required inputs:
tokenAddress– Contract addressamount– Amount to burn in smallest unit (BigInt)walletVerification– PINCODE verification
Validation checks:
- Caller has
supplyManagementrole - Caller has sufficient balance to burn
- Amount is greater than zero
Example:
import { from } from "dnum";
await client.token.burn({
tokenAddress: "0xABCD...",
amount: from("50", 18),
walletVerification: {
verificationType: "PINCODE",
secretVerificationCode: "123456",
},
});Use cases:
- Reduce supply after redemptions
- Adjust stablecoin supply to match collateral
- Retire tokens from circulation
Transfer tokens operation
Transfers send tokens from the caller's balance to a recipient. All transfers undergo compliance checks unless bypassed with a forced transfer.
Prerequisites:
- API key for authentication
- Token holder with sufficient balance
- Recipient must have registered identity
- Token must not be paused
- Sender and recipient addresses must not be frozen
Required inputs:
tokenAddress– Contract addressto– Recipient wallet addressamount– Amount to transfer in smallest unit (BigInt)walletVerification– PINCODE verification
Compliance checks (automatic):
- Sender has registered identity
- Recipient has registered identity
- Transfer satisfies all active compliance modules (e.g., allowlist, country restrictions, lock-up periods)
- Token is not paused
- Sender and recipient addresses are not frozen
Example:
import { from } from "dnum";
await client.token.transfer({
tokenAddress: "0xABCD...",
to: "0x1234...",
amount: from("25", 18),
walletVerification: {
verificationType: "PINCODE",
secretVerificationCode: "123456",
},
});Use cases:
- Send tokens to another investor
- Distribute tokens to multiple recipients
- Transfer tokens to a custody wallet
Forced transfer operation
Forced transfers bypass compliance checks and move tokens between addresses. This is a custodian operation used for regulatory interventions, court orders, or operational recovery.
Prerequisites:
- API key for authentication
custodiantoken role- Source wallet must have sufficient balance
- Destination wallet must not be frozen (source can be frozen)
Required inputs:
tokenAddress– Contract addressfrom– Source wallet addressto– Recipient wallet addressamount– Amount to transfer in smallest unit (BigInt)walletVerification– PINCODE verification
Compliance bypass:
Forced transfers skip all compliance checks including:
- Identity verification
- Allowlist restrictions
- Country/jurisdiction rules
- Lock-up periods
- Frozen sender addresses (but not frozen recipient addresses)
Example:
import { from } from "dnum";
await client.token.forcedTransfer({
tokenAddress: "0xABCD...",
from: "0x1234...", // Source wallet (can be frozen)
to: "0x5678...", // Destination (must not be frozen)
amount: from("100", 18),
walletVerification: {
verificationType: "PINCODE",
secretVerificationCode: "123456",
},
});Use cases:
- Regulatory seizure or forfeiture
- Court-ordered asset recovery
- Operational recovery from compromised wallets
- Resolving stuck transfers due to compliance failures
Audit trail:
Every forced transfer emits a ForcedTransfer event on-chain with:
from– Source addressto– Destination addressamount– Transferred amountexecutor– Custodian who executed the transfertimestamp– Block timestamp
Review forced transfers in the platform's audit log or via token.events.
Next steps

- Asset-specific guides – Follow step-by-step tutorials for each asset type:
- API reference – Explore the OpenAPI spec and generate clients