TypeScript SDK ๐ง
The DolphinPay TypeScript SDK provides a complete, type-safe interface for interacting with DolphinPay smart contracts on the Sui blockchain.
Featuresโ
- ๐ Type Safety: Full TypeScript support with comprehensive type definitions
- ๐งฉ Modular Design: Separate modules for Payment and Merchant operations
- โก Transaction Building: Build transactions without executing them for full control
- ๐งช Dry Run Testing: Test transactions before execution to estimate gas and catch errors
- ๐ Query Support: Query payment and merchant data from the blockchain
- ๐ ๏ธ Utility Functions: Helper functions for amount conversion, fee calculation, and validation
- ๐ Multi-Network: Support for mainnet, testnet, devnet, and localnet
- โ Testnet Ready: Deployed to Sui testnet and ready for integration testing
Installationโ
# npm
npm install @dolphinpay/sdk
# yarn
yarn add @dolphinpay/sdk
# bun
bun add @dolphinpay/sdk
Quick Startโ
1. Initialize Clientโ
import { createClient } from "@dolphinpay/sdk"
// Using testnet deployment
const client = createClient({
packageId:
"0x9c7ca262d020b005e0e6b6a5d083b329d58716e0d80c07b46804324074468f9c",
network: "testnet",
})
2. Create a Paymentโ
import { suiToMist } from "@dolphinpay/sdk"
// Build payment creation transaction
const txb = client.payment.buildCreatePayment({
merchant: "0xmerchant_address_here",
amount: suiToMist(10), // 10 SUI
currency: "SUI",
description: "Payment for premium subscription",
metadata: {
orderId: "ORDER-123",
customerId: "CUST-456",
},
expirySeconds: 3600, // 1 hour
})
// Execute with wallet
const result = await wallet.signAndExecuteTransactionBlock({
transactionBlock: txb,
})
console.log("Payment created:", result.digest)
3. Execute a Paymentโ
// Build payment execution transaction
const txb = client.payment.buildExecutePayment(
{
paymentId: "0xpayment_object_id",
coinObjectId: "0xcoin_object_id",
},
"0x2::sui::SUI"
) // Currency type
// Execute with wallet
const result = await wallet.signAndExecuteTransactionBlock({
transactionBlock: txb,
})
Client Configurationโ
Network Optionsโ
type Network = "mainnet" | "testnet" | "devnet" | "localnet"
const client = createClient({
packageId: "0x...", // Your deployed package ID
network: "testnet", // Network to use
rpcUrl: "https://...", // Optional: custom RPC endpoint
})
Custom RPC Endpointsโ
// Testnet
const testnetClient = createClient({
packageId: "0x...",
network: "testnet",
rpcUrl: "https://fullnode.testnet.sui.io:443",
})
// Mainnet
const mainnetClient = createClient({
packageId: "0x...",
network: "mainnet",
rpcUrl: "https://fullnode.mainnet.sui.io:443",
})
// Local development
const localClient = createClient({
packageId: "0x...",
network: "localnet",
rpcUrl: "http://127.0.0.1:9000",
})
Payment Operationsโ
Create Paymentโ
const txb = client.payment.buildCreatePayment({
merchant: "0xmerchant_address",
amount: suiToMist(100), // Amount in MIST (smallest unit)
currency: "0x2::sui::SUI", // Currency type name
description: "Product purchase", // Description (max 500 chars)
metadata: {
// Additional data (max 10 entries)
orderId: "12345",
customerEmail: "user@example.com",
},
expirySeconds: 3600, // Expiry time (1 hour)
})
Execute Paymentโ
const txb = client.payment.buildExecutePayment(
{
paymentId: "0xpayment_object_id", // Payment object ID
coinObjectId: "0xcoin_object_id", // Coin to use for payment
},
"0x2::sui::SUI"
) // Currency type
Cancel Paymentโ
const txb = client.payment.buildCancelPayment({
paymentId: "0xpayment_object_id", // Payment to cancel
merchantCapId: "0xmerchant_cap_id", // Merchant capability
})
Query Paymentโ
// Get full payment details
const payment = await client.payment.getPayment("0xpayment_id")
console.log("Amount:", payment.payment.amount)
console.log("Status:", payment.payment.status)
console.log("Merchant:", payment.payment.merchant)
// Get payment status only
const status = await client.payment.getPaymentStatus("0xpayment_id")
console.log("Status code:", status)
// Check if payment expired
const expired = await client.payment.isPaymentExpired("0xpayment_id")
console.log("Expired:", expired)
Merchant Operationsโ
Register Merchantโ
const txb = client.merchant.buildRegisterMerchant({
name: "My Online Store",
description: "E-commerce platform for digital goods",
feeConfig: {
customFeeBps: 50, // 0.5% custom fee
minFee: "1000000", // 0.001 SUI minimum
maxFee: "1000000000", // 1 SUI maximum
},
})
Configure Merchant Feesโ
const txb = client.merchant.buildConfigureMerchantFees({
merchantObjectId: "0xmerchant_object_id",
merchantCapId: "0xmerchant_cap_id",
customFeeBps: 100, // 1% custom fee
minFee: "1000000", // 0.001 SUI min
maxFee: "1000000000", // 1 SUI max
})
Add Currency Supportโ
const txb = client.merchant.buildAddSupportedCurrency({
merchantObjectId: "0xmerchant_object_id",
merchantCapId: "0xmerchant_cap_id",
currencyType: "0x2::sui::SUI",
receivingAddress: "0xmerchant_wallet_address",
})
Update Receiving Addressโ
const txb = client.merchant.buildSetReceivingAddress({
merchantObjectId: "0xmerchant_object_id",
merchantCapId: "0xmerchant_cap_id",
currencyType: "0x2::sui::SUI",
address: "0xnew_receiving_address",
})
Utility Functionsโ
Amount Conversionโ
import { suiToMist, mistToSui } from "@dolphinpay/sdk"
// Convert SUI to MIST (1 SUI = 1,000,000,000 MIST)
const mist = suiToMist(10) // "10000000000"
const sui = mistToSui("10000000000") // 10
Fee Calculationโ
import { calculateFee, calculateFeeBreakdown } from "@dolphinpay/sdk"
// Calculate single fee (30 bps = 0.3%)
const fee = calculateFee("10000000000", 30) // "30000000"
// Get full breakdown
const breakdown = calculateFeeBreakdown("10000000000", 50)
console.log(breakdown)
// {
// amount: "10000000000",
// platformFee: "30000000", // 0.3% platform fee
// merchantFee: "50000000", // 0.5% merchant fee
// totalFee: "80000000", // 0.8% total fee
// netAmount: "9920000000" // Amount after fees
// }
Validationโ
import {
validatePaymentAmount,
validateDescription,
validateMetadata,
validateExpiry,
} from "@dolphinpay/sdk"
// Validate payment amount
validatePaymentAmount(suiToMist(100)) // throws if invalid
// Validate description
validateDescription("Payment for order #123") // throws if too long
// Validate metadata
validateMetadata({ orderId: "123", customerId: "456" }) // throws if too many entries
// Validate expiry time
validateExpiry(3600) // throws if invalid range
Dry Run Testingโ
Test transactions before execution to catch errors and estimate gas:
// Test payment creation
const result = await client.payment.dryRunCreatePayment({
merchant: '0xmerchant_address',
amount: suiToMist(100),
currency: '0x2::sui::SUI',
description: 'Test payment',
metadata: {},
expirySeconds: 3600,
}, '0xuser_address'); // Sender address for dry run
if (result.success) {
console.log('โ
Transaction will succeed!');
console.log('Gas estimate:', result.effects.gasUsed);
console.log('Objects created:', result.objectChanges?.length);
// Now execute the real transaction
const txb = client.payment.buildCreatePayment({...});
await wallet.signAndExecuteTransactionBlock({ transactionBlock: txb });
} else {
console.error('โ Transaction would fail:', result.error);
// Fix the error before trying real transaction
}
Error Handlingโ
All SDK methods throw descriptive errors:
try {
const txb = client.payment.buildCreatePayment({
merchant: "0xinvalid_address",
amount: "-100", // Invalid amount
currency: "INVALID",
description: "Test",
})
} catch (error) {
console.error("Validation error:", error.message)
// "Amount must be greater than 0"
// "Invalid merchant address format"
// "Unsupported currency type"
}
Constants and Typesโ
Payment Constantsโ
import { PAYMENT_CONSTANTS } from "@dolphinpay/sdk"
console.log(PAYMENT_CONSTANTS.PLATFORM_FEE_BPS) // 30 (0.3%)
console.log(PAYMENT_CONSTANTS.MAX_PAYMENT_AMOUNT) // "1000000000000" (1000 SUI)
console.log(PAYMENT_CONSTANTS.MAX_DESCRIPTION_LENGTH) // 500
console.log(PAYMENT_CONSTANTS.DEFAULT_EXPIRY_SECONDS) // 3600 (1 hour)
Merchant Constantsโ
import { MERCHANT_CONSTANTS } from "@dolphinpay/sdk"
console.log(MERCHANT_CONSTANTS.MAX_CUSTOM_FEE_BPS) // 1000 (10%)
console.log(MERCHANT_CONSTANTS.MAX_NAME_LENGTH) // 100
Sui Typesโ
import { SUI_TYPES } from "@dolphinpay/sdk"
console.log(SUI_TYPES.SUI) // "0x2::sui::SUI"
console.log(SUI_TYPES.COIN) // "0x2::coin::Coin"
Event Handlingโ
Listen to blockchain events for real-time updates:
import { SuiClient } from "@mysten/sui.js/client"
// Create event listener
const suiClient = new SuiClient({ url: "https://fullnode.testnet.sui.io:443" })
// Listen for payment events
suiClient.subscribeEvent({
filter: {
MoveEventType: `${packageId}::events::PaymentCreated`,
},
onMessage: (event) => {
console.log("New payment created:", event.parsedJson)
},
})
Type Definitionsโ
The SDK exports comprehensive TypeScript types:
import type {
Payment,
PaymentStatus,
CreatePaymentParams,
Merchant,
FeeConfig,
RegisterMerchantParams,
Network,
ClientConfig,
// ... and many more
} from "@dolphinpay/sdk"
Testingโ
Integration Testsโ
# Install dependencies
npm install
# Run integration tests (requires testnet SUI)
npm run test:integration
Test Coverageโ
- โ Client initialization (12 tests)
- โ Payment module operations (12 tests)
- โ Merchant module operations (14 tests)
- โ Utility functions (16 tests)
- โ Error handling (8 tests)
- โ Dry run functionality (6 tests)
Examplesโ
See our comprehensive guides for complete working examples:
- SDK Initialization Guide - Client setup for different networks
- Payment Operations Guide - Complete payment lifecycle examples
- Merchant Operations Guide - Merchant management examples
- Basic Payment Example - Full integration example
Best Practicesโ
1. Always Validate Inputsโ
// โ
Good: Validate before building transaction
const amount = suiToMist(100)
validatePaymentAmount(amount)
const txb = client.payment.buildCreatePayment({
merchant: validateAddress(merchantAddress),
amount,
currency: "0x2::sui::SUI",
description: "Valid description",
metadata: {},
expirySeconds: 3600,
})
// โ Bad: Let SDK throw errors (wastes gas)
try {
const txb = client.payment.buildCreatePayment({
merchant: "invalid-address",
amount: "-100",
// ...
})
} catch (error) {
// Error caught, but user still pays for failed transaction
}
2. Use Dry Run for Testingโ
// โ
Good: Test first, then execute
const dryResult = await client.payment.dryRunCreatePayment(params, userAddress)
if (!dryResult.success) {
throw new Error(`Transaction would fail: ${dryResult.error}`)
}
const txb = client.payment.buildCreatePayment(params)
await wallet.signAndExecuteTransactionBlock({ transactionBlock: txb })
// โ Bad: Execute without testing (risky)
const txb = client.payment.buildCreatePayment(params)
await wallet.signAndExecuteTransactionBlock({ transactionBlock: txb })
3. Handle All Error Typesโ
// โ
Good: Comprehensive error handling
try {
const result = await wallet.signAndExecuteTransactionBlock({
transactionBlock: txb,
})
if (result.effects?.status?.error) {
throw new Error(`Transaction failed: ${result.effects.status.error}`)
}
console.log("Success:", result.digest)
} catch (error) {
if (error.message?.includes("insufficient")) {
// Handle insufficient balance
showBalanceError()
} else if (error.message?.includes("expired")) {
// Handle expired payment
showExpiryError()
} else {
// Handle other errors
showGenericError(error.message)
}
}
Migration Guideโ
Upgrading from v0.1.0โ
// Before (v0.1.0)
const client = new DolphinPayClient({
packageId: "0x...",
network: "testnet",
})
// After (v0.2.0+)
import { createClient } from "@dolphinpay/sdk"
const client = createClient({
packageId: "0x...",
network: "testnet",
})
Troubleshootingโ
Common Issuesโ
"Amount must be greater than 0"
// โ Wrong
client.payment.buildCreatePayment({
amount: 0, // Invalid!
// ...
})
// โ
Correct
client.payment.buildCreatePayment({
amount: suiToMist(0.1), // 0.1 SUI minimum
// ...
})
"Invalid merchant address format"
// โ Wrong
client.payment.buildCreatePayment({
merchant: "merchant_address", // Missing 0x prefix
// ...
})
// โ
Correct
client.payment.buildCreatePayment({
merchant: "0x1234567890abcdef...", // Valid Sui address
// ...
})
"Transaction would fail" (Dry Run)
// Check dry run result
const dryResult = await client.payment.dryRunCreatePayment(params, userAddress)
if (!dryResult.success) {
console.log("Error:", dryResult.error)
console.log("Gas estimate:", dryResult.effects?.gasUsed)
// Fix issues before real execution
}
Supportโ
- GitHub Issues: https://github.com/dolphinslab/dolphin-pay/issues
- Documentation: You're reading it! ๐
- SDK Examples: Check the Basic Payment Example
- Community: Join Sui Discord for community support
Ready to build something amazing? Check out the Basic Payment Example to see DolphinPay in action!