Open your platform wallet
Sign in and Dynamic provisions an embedded wallet you control. Deposit funds, then withdraw to any external wallet — pick the settlement token + chain when you do.
Pull from a Fireblocks vault, embedded wallet, or any external source and settle directly to the user's wallet of choice. Fireblocks Flow provides the swap, settlement, and webhook infrastructure[†].
Sign in and Dynamic provisions an embedded wallet you control. Deposit funds, then withdraw to any external wallet — pick the settlement token + chain when you do.
Your application should make clear to end-users that asset conversion and cross-chain routing are executed by independent third-party providers. Users keep full control of their assets and must explicitly sign each transfer. On-chain transactions are final and cannot be reversed.
By continuing, you agree to our Terms of Service and Privacy Policy.
Flow runs on mainnet networks only. Use a sandbox environment id with real mainnet addresses for development.
Server-side, one per withdraw. Creates a flow via POST /server/{envId}/flow/withdraw with the user's destination address in destinationConfig.destinations. The payout amount and settlement asset are fixed at creation time.
// Runs on your server — one Flow per payment/deposit/withdraw.
// Requires an API token with flow.write scope.
const res = await fetch(
`https://app.dynamic.xyz/api/v0/server/${process.env.ENV_ID}/flow/withdraw`,
{
method: "POST",
headers: {
Authorization: `Bearer ${process.env.DYNAMIC_API_KEY}`,
"Content-Type": "application/json",
},
body: JSON.stringify({
amount: "5.00",
currency: "USD",
settlementConfig: {
strategy: "preferred_order",
settlements: [
{
chainName: "SOL",
chainId: "101",
symbol: "USDC",
tokenAddress: "EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v",
tokenDecimals: 6,
},
],
},
destinationConfig: {
destinations: [
{
chainName: "SOL",
type: "address",
identifier: "0xUSER_EXTERNAL_WALLET",
},
],
},
}),
},
);
const { flow } = await res.json();
const flowId = flow.id;
// Pass flowId to your frontend.Declare the wallet funds are being withdrawn from. For this demo it's the embedded wallet Dynamic provisioned during connect. Returns a session token (dft_…); a 403 means the source is blocked even when it's user-controlled.
import { addEvmExtension } from "@dynamic-labs-sdk/evm";
import { attachFlowSource } from "@dynamic-labs-sdk/client";
addEvmExtension();
// Declare the payer's wallet + chain. Returns an updated flow and
// stores a session token (dft_…) for subsequent calls automatically.
await attachFlowSource({
flowId,
fromAddress: wallet.address,
fromChainId: String(fromChainId), // from the picked token — not getActiveNetworkData()
fromChainName: isSolanaChainId(fromToken.chainId) ? "SOL" : "EVM",
sourceType: "wallet",
});
// 403 → source blocked by risk/sanctions screening.Quote the swap from the picked source token in the embedded wallet to the settlement asset. Quotes expire in 60 seconds — re-quote if the user takes longer to confirm.
import { getFlowQuote } from "@dynamic-labs-sdk/client";
const quoted = await getFlowQuote({
flowId,
fromTokenAddress: fromToken.address,
fromChainId: String(fromToken.networkId),
slippage: 0.005, // 0.5%
});
// quoted.quote.expiresAt — re-quote if the user takes longer than 60s.The embedded wallet signs the on-chain transfer; Dynamic broadcasts and tracks settlement to the user-supplied destination address. SDK collapses prepare + sign + broadcast into submitFlowTransaction; REST keeps them separate.
import { submitFlowTransaction } from "@dynamic-labs-sdk/client";
// prepare → sign (wallet popup) → broadcast in one helper.
await submitFlowTransaction({
flowId,
walletAccount: wallet,
});Call getFlow to read executionState and settlementState. Production should subscribe to the flow.settlement.updated webhook for push-driven updates. On completed, the destination wallet has received the funds; on failed, expose a retry with a fresh flow.
import { getFlow } from "@dynamic-labs-sdk/client";
const flow = await getFlow({ flowId });
// flow.executionState — lifecycle phase (e.g. "source_confirmed", "failed")
// flow.settlementState — "none" | "completed" | "failed"
// flow.settlement — { txHash?, … } once settledDynamic does not control the swap, bridge, or routing protocols used to convert and deliver assets. Rates and fees are sourced from third-party providers and may change between quote and execution.
Cross-chain transfers carry risk — including slippage, partial fills, and failed conversions. On-chain transactions are final and cannot be reversed.
These materials are not investment, financial, legal, or tax advice. You are responsible for evaluation at your own discretion. Please review Dynamic's terms and conditions for full details on acceptable use.