Installation
Copy
npm install @centuari/credit-kit
# or
yarn add @centuari/credit-kit
# or
pnpm add @centuari/credit-kit
Quick Start
Copy
import { CreditKit } from '@centuari/credit-kit';
// Initialize client
const client = new CreditKit({
apiKey: process.env.CENTUARI_API_KEY,
environment: 'production' // or 'sandbox'
});
// Create a lending position
const position = await client.lend({
userId: 'user_123',
asset: 'USDC',
amount: '10000',
rate: 0.08,
maturity: '90d'
});
console.log(`Position created: ${position.positionId}`);
Configuration
Client Options
Copy
const client = new CreditKit({
// Required
apiKey: 'ck_live_...',
// Optional
environment: 'production', // 'production' | 'sandbox'
timeout: 30000, // Request timeout in ms
retries: 3, // Number of retries on failure
baseUrl: 'https://...', // Custom API URL (advanced)
});
Environment Variables
The SDK reads these environment variables:| Variable | Description |
|---|---|
CENTUARI_API_KEY | API key (if not passed to constructor) |
CENTUARI_ENV | Environment (production/sandbox) |
Lending Operations
Easy Mode Lending
Let the protocol optimize rate and maturity:Copy
const position = await client.easyLend({
userId: 'user_123',
asset: 'USDC',
amount: '10000'
});
// Position auto-optimized for best available rate
console.log(`Rate: ${position.rate * 100}% APY`);
console.log(`Maturity: ${position.maturity}`);
Advanced Mode Lending
Full control over parameters:Copy
const position = await client.lend({
userId: 'user_123',
asset: 'USDC',
amount: '10000',
rate: 0.085, // Exactly 8.5% APY
maturity: '2025-06-15', // Specific date
autoRollover: false // Manual control
});
Batch Lending
Create multiple positions efficiently:Copy
const positions = await client.batchLend([
{ userId: 'user_1', asset: 'USDC', amount: '10000' },
{ userId: 'user_2', asset: 'USDC', amount: '25000' },
{ userId: 'user_3', asset: 'USDT', amount: '15000' }
]);
console.log(`Created ${positions.length} positions`);
Borrowing Operations
Create Borrow Position
Copy
const position = await client.borrow({
userId: 'user_456',
collateral: {
asset: 'ETH',
amount: '5'
},
borrowAsset: 'USDC',
borrowAmount: '8000',
maturity: '90d',
autoRefinance: true
});
console.log(`Borrowed: ${position.borrowAmount} USDC`);
console.log(`Health Factor: ${position.healthFactor}`);
Check Borrowing Power
Copy
const power = await client.getBorrowingPower({
userId: 'user_456',
collateral: {
asset: 'ETH',
amount: '5'
},
borrowAsset: 'USDC'
});
console.log(`Max borrow: ${power.maxBorrow} USDC`);
console.log(`LTV: ${power.ltv * 100}%`);
Repay Loan
Copy
// Full repayment
await client.repay({
positionId: 'pos_xyz789'
});
// Partial repayment
await client.repay({
positionId: 'pos_xyz789',
amount: '4000'
});
Add Collateral
Copy
await client.addCollateral({
positionId: 'pos_xyz789',
asset: 'ETH',
amount: '1'
});
Position Management
Get Position
Copy
const position = await client.getPosition('pos_abc123');
console.log({
status: position.status,
amount: position.amount,
rate: position.rate,
maturity: position.maturity,
accruedInterest: position.accruedInterest
});
List Positions
Copy
// All positions for a user
const { positions, hasMore, nextCursor } = await client.listPositions({
userId: 'user_123',
status: 'active',
type: 'lend',
limit: 20
});
// Pagination
if (hasMore) {
const nextPage = await client.listPositions({
userId: 'user_123',
cursor: nextCursor
});
}
Cancel Order
Copy
await client.cancelOrder('pos_abc123');
Update Auto Features
Copy
await client.updatePosition('pos_abc123', {
autoRollover: false
});
User Management
Get User Summary
Copy
const summary = await client.getUserSummary('user_123');
console.log({
totalLent: summary.totalLent,
totalBorrowed: summary.totalBorrowed,
activePositions: summary.activePositions,
totalEarned: summary.totalEarned
});
Get User Balances
Copy
const balances = await client.getUserBalances('user_123');
for (const balance of balances) {
console.log(`${balance.asset}: ${balance.available} available`);
}
Withdraw Funds
Copy
const withdrawal = await client.withdraw({
userId: 'user_123',
asset: 'USDC',
amount: '5000',
destination: '0x...'
});
console.log(`Withdrawal ID: ${withdrawal.id}`);
console.log(`Status: ${withdrawal.status}`);
Market Data
Get Current Rates
Copy
const rates = await client.getRates();
for (const rate of rates) {
console.log(`${rate.asset} ${rate.maturity}: Lend ${rate.lendRate * 100}%, Borrow ${rate.borrowRate * 100}%`);
}
Get Order Book
Copy
const orderBook = await client.getOrderBook({
asset: 'USDC',
maturity: '90d',
depth: 10
});
console.log('Lend orders:', orderBook.lends);
console.log('Borrow orders:', orderBook.borrows);
Get Market Stats
Copy
const stats = await client.getMarketStats('USDC');
console.log({
totalLent: stats.totalLent,
totalBorrowed: stats.totalBorrowed,
averageRate: stats.averageRate
});
Webhooks
Webhook Handler
Copy
import express from 'express';
import { CreditKit } from '@centuari/credit-kit';
const app = express();
app.post('/webhooks/centuari', express.raw({ type: 'application/json' }), (req, res) => {
const signature = req.headers['x-centuari-signature'] as string;
try {
const event = CreditKit.verifyWebhook(
req.body,
signature,
process.env.WEBHOOK_SECRET
);
switch (event.type) {
case 'position.matched':
console.log(`Position matched: ${event.data.positionId}`);
break;
case 'position.matured':
console.log(`Position matured: ${event.data.positionId}`);
break;
case 'position.liquidated':
console.log(`Position liquidated: ${event.data.positionId}`);
break;
}
res.json({ received: true });
} catch (err) {
console.error('Webhook error:', err);
res.status(400).json({ error: 'Invalid signature' });
}
});
Event Types
Copy
import { WebhookEvent } from '@centuari/credit-kit';
type PositionMatchedEvent = WebhookEvent<'position.matched'>;
type PositionMaturedEvent = WebhookEvent<'position.matured'>;
type PositionLiquidatedEvent = WebhookEvent<'position.liquidated'>;
Error Handling
Error Types
Copy
import {
CreditKitError,
AuthenticationError,
ValidationError,
InsufficientFundsError,
RateLimitError
} from '@centuari/credit-kit';
try {
await client.lend({ ... });
} catch (error) {
if (error instanceof InsufficientFundsError) {
console.log(`Need ${error.required}, have ${error.available}`);
} else if (error instanceof RateLimitError) {
console.log(`Retry after ${error.retryAfter}ms`);
} else if (error instanceof CreditKitError) {
console.log(`Error: ${error.code} - ${error.message}`);
}
}
Retries
Built-in retry logic for transient failures:Copy
const client = new CreditKit({
apiKey: '...',
retries: 3, // Number of retries
retryDelay: 1000, // Initial delay (ms)
retryBackoff: 2 // Exponential backoff multiplier
});
TypeScript Support
Full TypeScript support with types:Copy
import {
CreditKit,
Position,
LendParams,
BorrowParams,
PositionStatus,
Asset
} from '@centuari/credit-kit';
const params: LendParams = {
userId: 'user_123',
asset: 'USDC' as Asset,
amount: '10000',
rate: 0.08
};
const position: Position = await client.lend(params);
Testing
Mock Client
Copy
import { MockCreditKit } from '@centuari/credit-kit/testing';
const mockClient = new MockCreditKit();
// Configure mock responses
mockClient.onLend().resolves({
positionId: 'mock_pos_123',
status: 'active',
rate: 0.08
});
// Use in tests
const position = await mockClient.lend({ ... });
expect(position.positionId).toBe('mock_pos_123');
Sandbox Testing
Copy
const sandbox = new CreditKit({
apiKey: 'ck_test_...',
environment: 'sandbox'
});
// Test with fake tokens
const position = await sandbox.lend({
userId: 'test_user',
asset: 'USDC',
amount: '1000000' // Test with any amount
});
Examples
Complete Integration Example
Copy
import { CreditKit } from '@centuari/credit-kit';
import express from 'express';
const client = new CreditKit({ apiKey: process.env.API_KEY });
const app = express();
// User wants to lend
app.post('/api/lend', async (req, res) => {
const { userId, amount } = req.body;
try {
const position = await client.easyLend({
userId,
asset: 'USDC',
amount
});
res.json({
success: true,
position: {
id: position.positionId,
rate: `${(position.rate * 100).toFixed(2)}%`,
maturity: position.maturity,
projectedReturn: position.projectedReturn
}
});
} catch (error) {
res.status(400).json({ error: error.message });
}
});
// User checks their positions
app.get('/api/positions/:userId', async (req, res) => {
const { positions } = await client.listPositions({
userId: req.params.userId
});
res.json({ positions });
});
// Webhook handler
app.post('/webhooks', express.raw({ type: 'application/json' }), (req, res) => {
const event = CreditKit.verifyWebhook(req.body, req.headers['x-centuari-signature'], process.env.WEBHOOK_SECRET);
// Handle event...
res.json({ received: true });
});
app.listen(3000);
API Reference
View complete API documentation