Overview
This guide covers treasury and partner administration operations:
- Withdrawals — move USDC or Gold from your partner PDA to an external wallet
- Executive authority rotation — add or remove wallets that can sign trading transactions
- Batch transaction submission — submit multiple signed transactions at once
Withdrawals
Withdrawals move funds from your partner PDA (centralVaultAddress) to the withdrawal authority wallet. This destination is fixed and cannot be changed. You can withdraw either USDC or Gold tokens.
Withdrawals require an API key with PARTNER_WITHDRAWAL_AUTHORITY scope. This is a separate key from the executive authority key used for trading.
Step 1: Create a Withdrawal Transaction
Withdraw USDC
curl -X POST https://oro-tradebook-devnet.up.railway.app/api/trading/withdrawals \
-H "Content-Type: application/json" \
-H "x-api-key: your-withdrawal-api-key" \
-d '{
"amount": 1000,
"tokenType": "usdc"
}'
Withdraw Gold
curl -X POST https://oro-tradebook-devnet.up.railway.app/api/trading/withdrawals \
-H "Content-Type: application/json" \
-H "x-api-key: your-withdrawal-api-key" \
-d '{
"amount": 0.5,
"tokenType": "gold"
}'
Withdrawn funds are sent to the token account associated with your withdrawal authority wallet. There is no separate destination address field.
Both return the same response shape:
{
"success": true,
"data": {
"withdrawalId": "uuid-withdrawal-id",
"amount": 1000,
"tokenType": "usdc",
"status": "pending_signature",
"transaction": {
"serializedTx": "base64-encoded-transaction",
"signingInstructions": {
"walletType": "withdrawal_authority",
"signers": ["WithdrawalAuthorityAddress"],
"expiresAt": "2024-01-15T10:35:00.000Z"
}
},
"createdAt": "2024-01-15T10:30:00.000Z"
}
}
Step 2: Sign and Submit
The withdrawal authority key is separate from the executive authority key. Using the wrong key will fail signing. Verify your withdrawalAuthorityAddress via GET /api/distribution/partner/me.
Withdrawal transactions are Legacy Transactions signed by the withdrawal authority wallet only.
import { Keypair, Transaction, Connection, sendAndConfirmTransaction } from "@solana/web3.js";
const connection = new Connection("https://api.devnet.solana.com");
// Your withdrawal authority keypair
const withdrawalAuthority = Keypair.fromSecretKey(/* your secret key bytes */);
// Deserialize the transaction
const serializedTx = "base64-encoded-transaction"; // from response.data.transaction.serializedTx
const transaction = Transaction.from(Buffer.from(serializedTx, "base64"));
// Sign and send to Solana
const txId = await sendAndConfirmTransaction(connection, transaction, [withdrawalAuthority]);
console.log("Transaction ID:", txId);
If you prefer not to send the transaction yourself, you can use the POST /api/transactions/submit endpoint instead. Just pass the base64-encoded signed transaction and the API will send it to the network for you.
Executive Authority Rotation
Executive authority wallets control trading operations (buy, sell, user creation). You can add or remove these wallets as your team changes.
This operation requires an API key with PARTNER_UPDATE_AUTHORITY scope.
Add and Remove Wallets
curl -X PUT https://oro-tradebook-devnet.up.railway.app/api/distribution/partner/1/executive-authority \
-H "Content-Type: application/json" \
-H "x-api-key: your-update-api-key" \
-d '{
"add": ["NewWalletAddress"],
"remove": ["OldWalletAddress"]
}'
{
"success": true,
"data": {
"partnerId": "1",
"transaction": {
"serializedTx": "base64-encoded-transaction",
"signingInstructions": {
"walletType": "update_authority",
"signers": ["UpdateAuthorityAddress"],
"expiresAt": "2024-01-15T10:35:00.000Z"
}
}
}
}
Sign and Submit
You can add and remove wallets in a single request. The transaction atomically applies both changes.
After removing an executive authority wallet, any API keys generated from that wallet will still work but can no longer sign transactions. Revoke the associated API keys as well.
This is a Legacy Transaction signed by the update authority wallet.
import { Keypair, Transaction, Connection, sendAndConfirmTransaction } from "@solana/web3.js";
const connection = new Connection("https://api.devnet.solana.com");
const updateAuthority = Keypair.fromSecretKey(/* update authority secret key */);
const serializedTx = "base64-encoded-transaction";
const transaction = Transaction.from(Buffer.from(serializedTx, "base64"));
// Sign and send to Solana
const txId = await sendAndConfirmTransaction(connection, transaction, [updateAuthority]);
console.log("Transaction ID:", txId);
If you prefer not to send the transaction yourself, you can use the POST /api/transactions/submit endpoint instead. Just pass the base64-encoded signed transaction and the API will send it to the network for you.
Batch Transaction Submission
Use batch submission when processing multiple user trades at once. Sign each transaction individually, collect them into an array, and submit in a single request.
When you need to submit multiple signed transactions (e.g., bulk user purchases), use the batch endpoint instead of submitting one at a time.
curl -X POST https://oro-tradebook-devnet.up.railway.app/api/transactions/submit/all \
-H "Content-Type: application/json" \
-d '{
"transactions": [
"base64-signed-tx-1",
"base64-signed-tx-2",
"base64-signed-tx-3"
]
}'
{
"success": true,
"data": [
{
"txId": "5UfDuX...",
"status": "confirmed"
},
{
"txId": "7GhKlM...",
"status": "confirmed"
},
{
"txId": "9AbCdE...",
"status": "failed",
"error": "Transaction simulation failed"
}
]
}
Key details about batch submission:
- All transactions are processed concurrently
- Each transaction is submitted independently — partial success is possible
- Results are returned for all transactions, including failures
- This endpoint is public (no authentication required)
Summary: Authority Key Reference
| Operation | Required Scope | Signing Wallet |
|---|
| Buy / Sell gold | PARTNER_EXECUTIVE_AUTHORITY | Executive authority |
| Create users | PARTNER_EXECUTIVE_AUTHORITY | Executive authority |
| Withdraw funds | PARTNER_WITHDRAWAL_AUTHORITY | Withdrawal authority |
| Rotate wallets | PARTNER_UPDATE_AUTHORITY | Update authority |
| List / Revoke keys | PARTNER_UPDATE_AUTHORITY | — (API key only) |
| Submit transactions | Public | — (no auth) |