Manage ICP cycles for canister operations
import { ICPAgent } from 'icp-agent-kit';
const agent = new ICPAgent({ network: 'local' });
// Get cycles balance
const balance = await agent.cyclesPlugin.getBalance('rdmx6-jaaaa-aaaaa-aaadq-cai');
console.log(`Balance: ${agent.cyclesPlugin.formatCycles(balance.balance)}`);
// Top up a canister
await agent.cyclesPlugin.topUp('rdmx6-jaaaa-aaaaa-aaadq-cai', '2T');
// Transfer cycles between canisters
await agent.cyclesPlugin.transfer({
from: 'rdmx6-jaaaa-aaaaa-aaadq-cai',
to: 'rrkah-fqaaa-aaaaa-aaaaq-cai',
amount: BigInt(1_000_000_000_000) // 1T cycles
});
// Get detailed balance information
const balance = await agent.cyclesPlugin.getBalance('canister-id');
console.log({
balance: balance.balance,
freezingThreshold: balance.freezingThreshold,
memoryUsage: balance.memoryUsage,
estimatedDaysUntilFrozen: balance.estimatedDaysUntilFrozen
});
// Check multiple canisters at once
const balances = await agent.cyclesPlugin.getBatchBalances([
'canister-1',
'canister-2',
'canister-3'
]);
// Top up with different amount formats
await agent.cyclesPlugin.topUp('canister-id', '2T'); // 2 trillion cycles
await agent.cyclesPlugin.topUp('canister-id', '500GC'); // 500 billion cycles
await agent.cyclesPlugin.topUp('canister-id', BigInt(1e12)); // 1 trillion cycles
// Batch top-up multiple canisters
const results = await agent.cyclesPlugin.batchTopUp([
{ canisterId: 'canister-1', amount: '1T' },
{ canisterId: 'canister-2', amount: '2T' },
{ canisterId: 'canister-3', amount: '500GC' }
]);
// Check results
results.forEach(result => {
if (result.success) {
console.log(`✓ ${result.canisterId} topped up successfully`);
} else {
console.log(`✗ ${result.canisterId} failed: ${result.error}`);
}
});
// Convert ICP to cycles
const conversion = await agent.cyclesPlugin.convertIcpToCycles(
BigInt(100_000_000), // 1 ICP (in e8s)
{
targetCanister: 'canister-id', // Optional: auto top-up target
xdrRate: 5.0 // Optional: custom XDR rate
}
);
console.log({
icpUsed: conversion.icpUsed,
cyclesReceived: conversion.cyclesReceived,
conversionRate: conversion.conversionRate,
transactionId: conversion.transactionId
});
// Get current pricing information
const pricing = await agent.cyclesPlugin.getPricing();
console.log({
xdrToCycles: pricing.xdrToCycles,
icpToXdr: pricing.icpToXdr,
icpToCycles: pricing.icpToCycles
});
// Get usage metrics for different time periods
const dailyMetrics = await agent.cyclesPlugin.getUsageMetrics('canister-id', 'day');
const weeklyMetrics = await agent.cyclesPlugin.getUsageMetrics('canister-id', 'week');
dailyMetrics.forEach(metric => {
console.log({
period: metric.period,
totalConsumed: metric.totalConsumed,
computeCycles: metric.computeCycles,
memoryCycles: metric.memoryCycles,
networkCycles: metric.networkCycles,
averageConsumptionRate: metric.averageConsumptionRate
});
});
// Get consumption forecast
const forecast = await agent.cyclesPlugin.getForecast('canister-id');
console.log({
currentBalance: forecast.currentBalance,
daysUntilDepletion: forecast.daysUntilDepletion,
depletionDate: forecast.depletionDate,
recommendedTopUp: forecast.recommendedTopUp,
confidence: forecast.confidence
});
// Start monitoring canisters for low cycles
await agent.cyclesPlugin.startMonitoring({
canisterIds: ['canister-1', 'canister-2'],
lowBalanceThreshold: BigInt(1_000_000_000_000), // 1T cycles
checkInterval: 300, // Check every 5 minutes
autoTopUp: {
enabled: true,
topUpAmount: BigInt(2_000_000_000_000), // 2T cycles
maxTopUpsPerDay: 3
}
});
// Check for alerts
const alerts = agent.cyclesPlugin.getAlerts();
alerts.forEach(alert => {
console.log({
type: alert.type,
severity: alert.severity,
canisterId: alert.canisterId.toText(),
message: alert.message,
currentBalance: alert.currentBalance,
timestamp: alert.timestamp
});
});
// Stop monitoring
agent.cyclesPlugin.stopMonitoring();
// Clear all alerts
agent.cyclesPlugin.clearAlerts();
// Format cycles for display
const formatted = agent.cyclesPlugin.formatCycles(BigInt(2_500_000_000_000));
console.log(formatted); // "2.500 TC"
// Parse cycles from strings
const amount = agent.cyclesPlugin.parseCycles('1.5T');
console.log(amount); // 1500000000000n
// Validate amounts
const isValid = agent.cyclesPlugin.validateAmount('2T');
console.log(isValid); // 2000000000000n (throws error if invalid)
// Check if canister exists
const exists = await agent.cyclesPlugin.canisterExists('canister-id');
console.log(exists); // true/false
// Get formatted balance summary
const summary = await agent.cyclesPlugin.getBalanceSummary('canister-id');
console.log(summary);
/*
Canister: rdmx6-jaaaa-aaaaa-aaadq-cai
Balance: 2.500 TC
Status: healthy (Cycles balance is healthy)
Memory Usage: 1.50 MB
Daily Consumption: 127.00 GC
Estimated Days Until Depletion: 19
*/
// Estimate future consumption
const estimatedConsumption = await agent.cyclesPlugin.estimateConsumption('canister-id', 30);
console.log(`30-day estimate: ${agent.cyclesPlugin.formatCycles(estimatedConsumption)}`);
import { CyclesLedgerClient } from 'icp-agent-kit/cycles/ledger';
// Create ledger client
const ledgerClient = new CyclesLedgerClient(agent.agent, {
network: 'mainnet',
canisterId: 'um5iw-rqaaa-aaaaq-aab2q-cai'
});
// Create account
const account = CyclesLedgerClient.createAccount(
Principal.fromText('your-principal'),
CyclesLedgerClient.createDefaultSubaccount()
);
// Get ledger balance
const ledgerBalance = await ledgerClient.getBalance(account);
// Transfer via ledger
const transferResult = await ledgerClient.transfer({
to: account,
amount: BigInt(1_000_000_000_000),
memo: new TextEncoder().encode('Transfer memo')
});
// Get transaction history
const transactions = await ledgerClient.getTransactions({
start: 0n,
length: 10n
});
import { ICPAgentError } from 'icp-agent-kit';
try {
await agent.cyclesPlugin.topUp('invalid-canister', '1T');
} catch (error) {
if (error instanceof ICPAgentError) {
switch (error.code) {
case 'INSUFFICIENT_CYCLES':
console.log('Not enough cycles for operation');
break;
case 'INVALID_CANISTER_ID':
console.log('Invalid canister ID format');
break;
case 'AMOUNT_TOO_SMALL':
console.log('Amount below minimum required');
break;
case 'NETWORK_ERROR':
console.log('Network connectivity issue');
break;
default:
console.log(`Unexpected error: ${error.message}`);
}
}
}
// The cycles plugin is automatically loaded with default settings
const agent = new ICPAgent({
network: 'mainnet', // or 'local'
// Plugin will use appropriate canister IDs for the network
});
// Access plugin methods directly
const balance = await agent.cyclesPlugin.getBalance('canister-id');
'1T'
= 1,000,000,000,000 cycles'500GC'
= 500,000,000,000 cycles'2.5T'
= 2,500,000,000,000 cycles