DApp integration
How TRON DApps connect to user wallets, request authorization, sign and broadcast transactions. Two integration paths: TronWallet Adapter (recommended for unified multi-wallet support) and direct TronLink integration (for TronLink-specific customization).
A TRON DApp talks to the network through a wallet that the user already trusts. The DApp constructs a transaction; the wallet asks the user to approve it; the wallet signs and (usually) broadcasts. The DApp also reacts to wallet-level state changes — account switch, network switch, connect, disconnect.
This page covers DApp-side integration. If you are building a wallet yourself, see Wallet developer guide instead.
Prerequisites
What DApp integration covers
- Detecting a wallet's presence in the user's browser
- Requesting user authorization to read their address
- Building transactions and asking the wallet to sign
- Broadcasting signed transactions
- Listening to wallet events — account change, network change, connect, disconnect
- Adding your token to the wallet's asset list
- Switching the user's selected network (Mainnet / Shasta / Nile)
Two integration approaches
Two paths exist on TRON. They are not exclusive — many DApps support both.
| Approach | Wallets supported | Best for |
|---|---|---|
| TronWallet Adapter | TronLink, Bitkeep, OKX Wallet, Ledger via TronLink, and any wallet the Adapter ships support for | One unified integration. New wallets become available automatically as the Adapter adds support — no DApp code change |
| Direct TronLink | TronLink only | Easier to learn and debug; DApps with TronLink-specific customization that the uniform Adapter API does not expose |
The Adapter abstracts the wallet layer behind a uniform API, so adding a new wallet later does not require changing your DApp code. It is documented separately at TronWallet Adapter.
Direct TronLink integration is simpler to learn and to debug because there is no abstraction between your code and the wallet. The concepts — object injection, request and response, event flow — are the same in both paths; the Adapter just wraps them.
Approach 1: TronWallet Adapter (recommended)
TronWallet Adapter is the multi-wallet abstraction layer for TRON DApps. Your DApp writes against a stable uniform API; the Adapter handles per-wallet differences and inherits new wallet support as the Adapter ecosystem grows.
Typical use: install the Adapter package, mount its connection UI, and call its signTransaction / signMessage methods. The Adapter prompts the user to pick from available wallets, handles the chosen wallet's protocol, and returns a signed result that your DApp can broadcast.
Full reference — installation, supported wallet list, framework adapters (React, Vue, plain JavaScript), and signing API — is at TronWallet Adapter.
Approach 2: Direct TronLink integration
TronLink is the dominant TRON browser-extension wallet (comparable to MetaMask on Ethereum). When installed, it injects a provider object at window.tron that exposes a request/response API plus an event stream. Your DApp uses this provider to request authorization, read the user's address through provider.tronWeb, build and sign transactions, and listen for state changes.
TronLink maintains its own developer documentation at docs.tronlink.org. The sections below summarize the current API surface and link to the upstream reference for each integration concern.
API modernization (2025)The TronLink DApp API has been modernized. The current provider lives at
window.tron(notwindow.tronLink), authorization useseth_requestAccounts(nottron_requestAccounts), detection follows the TIP-6963 multi-wallet discovery standard, and events are subscribed viaprovider.on(event, callback)rather thanwindow.addEventListener('message', ...). The legacy entry points still work for backward compatibility but new integrations should use the modern surface described below.
The window.tron provider object
window.tron provider objectTronLink injects a provider implementing this shape into every page:
interface TronProvider {
isTronLink: true;
request: (args: { method: string; params?: any }) => Promise<any>;
tronWeb: TronWeb | false;
on(event: string, listener: (...args: any[]) => void): this;
removeListener(event: string, listener: (...args: any[]) => void): this;
}request(...)— the JSON-RPC-style entry point for active calls (eth_requestAccounts,wallet_watchAsset,wallet_switchEthereumChain).tronWeb—falseuntil the user authorizes this origin. After authorization succeeds it becomes a usable TronWeb instance for building and signing transactions.on(event, ...)/removeListener(event, ...)— subscribe to or detach from passive provider events (accountsChanged,chainChanged,connect,disconnect).
Capability summary
| Capability | API | Reference |
|---|---|---|
| Detect TronLink in the page | TIP-6963 (TIP6963:announceProvider event, fallback to window.tron) | docs.tronlink.org / DApp / Start developing |
| Request user authorization | provider.request({ method: 'eth_requestAccounts' }) | docs.tronlink.org / DApp / Start developing |
| Send a TRX transfer (build → sign → broadcast) | tronweb.transactionBuilder.sendTrx → tronweb.trx.sign → tronweb.trx.sendRawTransaction | docs.tronlink.org / DApp / General Transfer |
| Multi-signature transfer | tronweb.transactionBuilder.sendTrx(to, amount, { permissionId }) → tronweb.trx.multiSign(tx, undefined, permissionId) | docs.tronlink.org / DApp / Multi-Signature Transfer |
| Sign an arbitrary message | tronweb.trx.signMessageV2(hexString) | docs.tronlink.org / DApp / Message Signature |
| Stake 2.0 resource delegation / undelegation | tronweb.transactionBuilder.delegateResource(...) with __options.estimatedBandwidth / estimatedEnergy annotations | docs.tronlink.org / DApp / Stake2.0 |
| Add a token to the user's asset list | provider.request({ method: 'wallet_watchAsset', params: { type, options } }) (type is one of trc10, trc20, or trc721) | docs.tronlink.org / Plugin / Request TronLink Extension |
| Switch the user's selected network | provider.request({ method: 'wallet_switchEthereumChain', params: [{ chainId }] }) (TIP-3326) | docs.tronlink.org / Plugin / Request TronLink Extension |
| Subscribe to account / network / connect events | provider.on(event, callback) — events: accountsChanged, chainChanged, connect, disconnect | docs.tronlink.org / Plugin / Receive messages from TronLink |
Handle Ledger-signed transactions (v field) | The trailing byte changes — 00 → 1b, 01 → 1c — to match the regular signing format | docs.tronlink.org / Plugin / Ledger signing update |
Chain identifiers
TronLink uses Ethereum-style hex chain IDs for chainChanged and wallet_switchEthereumChain:
| Network | Chain ID |
|---|---|
| Mainnet | 0x2b6653dc |
| Shasta testnet | 0x94a9059e |
| Nile testnet | 0xcd8690dc |
Where to go next
This page covers the orientation a TRON developer needs to choose between TronWallet Adapter and direct integration, plus the shape of the window.tron provider and chain IDs. For everything else — including:
- The full
request(...)error code list and error semantics - Quick-start code samples (TIP-6963 detection,
eth_requestAccountsauthorization, build / sign / broadcast) - Event subscriptions (
accountsChanged,chainChanged,connect,disconnect,unlock,lock) - Legacy API migration mapping (
window.tronLink/tron_requestAccounts→ modernwindow.tron/eth_requestAccounts)
— see the TronLink developer documentation, the canonical TronLink reference.
Related resources
- TronWallet Adapter — multi-wallet abstraction (recommended for production DApps)
- TronWeb documentation — JavaScript SDK for building and signing transactions
- TronLink developer documentation — the canonical TronLink reference (full API, error codes, code samples, legacy migration)
- Transactions — transaction structure and signing lifecycle
- Smart contracts — calling smart contracts from a DApp
Updated 9 days ago