@fenelabs/fene-sdk 0.3.0 → 0.3.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +152 -343
- package/dist/index.d.mts +268 -895
- package/dist/index.d.ts +268 -895
- package/dist/index.js +344 -899
- package/dist/index.mjs +334 -890
- package/package.json +28 -42
- package/CHANGELOG.md +0 -152
package/README.md
CHANGED
|
@@ -1,429 +1,238 @@
|
|
|
1
|
-
#
|
|
1
|
+
# @resonance/sdk
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
TypeScript SDK for the Resonance API.
|
|
4
4
|
|
|
5
5
|
## Installation
|
|
6
6
|
|
|
7
7
|
```bash
|
|
8
|
-
|
|
9
|
-
# or
|
|
10
|
-
yarn add @fenelabs/fene-sdk
|
|
11
|
-
# or
|
|
12
|
-
pnpm add @fenelabs/fene-sdk
|
|
8
|
+
pnpm add @resonance/sdk
|
|
13
9
|
```
|
|
14
10
|
|
|
15
11
|
## Quick Start
|
|
16
12
|
|
|
17
13
|
```typescript
|
|
18
|
-
import {
|
|
14
|
+
import { createResonanceClient } from "@resonance/sdk";
|
|
19
15
|
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
apiUrl: 'https://api.fene.network',
|
|
23
|
-
timeout: 30000, // Optional, default 30s
|
|
16
|
+
const client = createResonanceClient({
|
|
17
|
+
baseUrl: "https://api.fene.network",
|
|
24
18
|
});
|
|
25
19
|
|
|
26
|
-
// Get
|
|
27
|
-
const stats = await
|
|
28
|
-
console.log(
|
|
20
|
+
// Get network stats
|
|
21
|
+
const stats = await client.getNetworkStats();
|
|
22
|
+
console.log(`Total validators: ${stats.total_validators}`);
|
|
29
23
|
|
|
30
|
-
// Get
|
|
31
|
-
const
|
|
32
|
-
console.log(
|
|
24
|
+
// Get APR
|
|
25
|
+
const apr = await client.getNetworkAPR();
|
|
26
|
+
console.log(`Network APR: ${apr.network_apr}%`);
|
|
33
27
|
```
|
|
34
28
|
|
|
35
29
|
## Authentication
|
|
36
30
|
|
|
37
|
-
The SDK supports wallet-based authentication using Web3 providers:
|
|
38
|
-
|
|
39
31
|
```typescript
|
|
40
|
-
import {
|
|
41
|
-
import {
|
|
32
|
+
import { createResonanceClient } from "@resonance/sdk";
|
|
33
|
+
import { signMessage } from "viem/wallet";
|
|
42
34
|
|
|
43
|
-
const
|
|
44
|
-
|
|
35
|
+
const client = createResonanceClient({
|
|
36
|
+
baseUrl: "https://api.fene.network",
|
|
37
|
+
onTokenExpired: () => {
|
|
38
|
+
console.log("Token expired, please re-authenticate");
|
|
39
|
+
},
|
|
45
40
|
});
|
|
46
41
|
|
|
47
|
-
//
|
|
48
|
-
const
|
|
49
|
-
const authResponse = await sdk.auth.connectWallet(provider, 'delegator');
|
|
42
|
+
// 1. Get nonce
|
|
43
|
+
const { message } = await client.getNonce("0x...");
|
|
50
44
|
|
|
51
|
-
//
|
|
52
|
-
|
|
45
|
+
// 2. Sign message (using viem or wagmi)
|
|
46
|
+
const signature = await signMessage({ message });
|
|
53
47
|
|
|
54
|
-
//
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
}
|
|
48
|
+
// 3. Verify and get JWT
|
|
49
|
+
const auth = await client.verify("0x...", signature);
|
|
50
|
+
console.log(`Logged in as: ${auth.role}`);
|
|
58
51
|
|
|
59
|
-
//
|
|
60
|
-
|
|
52
|
+
// Now authenticated requests work
|
|
53
|
+
await client.updateGeoLocation({ latitude: 0, longitude: 0, node_type: "rpc" });
|
|
61
54
|
```
|
|
62
55
|
|
|
63
|
-
##
|
|
56
|
+
## Error Handling
|
|
64
57
|
|
|
65
|
-
|
|
58
|
+
The SDK provides structured error handling matching the API's error system:
|
|
66
59
|
|
|
67
60
|
```typescript
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
const breakdown = await sdk.global.getNetworkAPRBreakdown();
|
|
61
|
+
import {
|
|
62
|
+
createResonanceClient,
|
|
63
|
+
ResonanceError,
|
|
64
|
+
ErrorCode,
|
|
65
|
+
isAuthError,
|
|
66
|
+
isNotFoundError,
|
|
67
|
+
} from "@resonance/sdk";
|
|
76
68
|
|
|
77
|
-
|
|
78
|
-
const delegatorLeaderboard = await sdk.global.getLeaderboardDelegators(10, 0);
|
|
79
|
-
|
|
80
|
-
// Get validator leaderboard
|
|
81
|
-
const validatorLeaderboard = await sdk.global.getLeaderboardValidators(10, 0);
|
|
82
|
-
```
|
|
83
|
-
|
|
84
|
-
### Validators
|
|
85
|
-
|
|
86
|
-
```typescript
|
|
87
|
-
// Get all validators
|
|
88
|
-
const allValidators = await sdk.validators.getAll();
|
|
69
|
+
const client = createResonanceClient({ baseUrl: "https://api.fene.network" });
|
|
89
70
|
|
|
90
|
-
|
|
91
|
-
const validator = await
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
//
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
// Get validator slashing events
|
|
112
|
-
const slashing = await sdk.validators.getSlashing('0x1234...');
|
|
113
|
-
|
|
114
|
-
// Get validator APR
|
|
115
|
-
const validatorAPR = await sdk.validators.getAPR('0x1234...');
|
|
71
|
+
try {
|
|
72
|
+
const validator = await client.getValidator("0xinvalid");
|
|
73
|
+
} catch (error) {
|
|
74
|
+
if (error instanceof ResonanceError) {
|
|
75
|
+
console.log(`Error code: ${error.code}`);
|
|
76
|
+
console.log(`Message: ${error.message}`);
|
|
77
|
+
console.log(`Status: ${error.statusCode}`);
|
|
78
|
+
|
|
79
|
+
// Check specific error types
|
|
80
|
+
if (error.is(ErrorCode.VALIDATOR_NOT_FOUND)) {
|
|
81
|
+
// Handle validator not found
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
// Or use helper functions
|
|
85
|
+
if (isAuthError(error)) {
|
|
86
|
+
// Re-authenticate
|
|
87
|
+
} else if (isNotFoundError(error)) {
|
|
88
|
+
// Handle not found
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
}
|
|
116
92
|
```
|
|
117
93
|
|
|
118
|
-
###
|
|
119
|
-
|
|
120
|
-
```typescript
|
|
121
|
-
// Get all delegators
|
|
122
|
-
const allDelegators = await sdk.delegators.getAll();
|
|
123
|
-
|
|
124
|
-
// Get specific delegator details
|
|
125
|
-
const delegator = await sdk.delegators.get('0xabcd...');
|
|
126
|
-
|
|
127
|
-
// Get delegator stakes breakdown
|
|
128
|
-
const stakes = await sdk.delegators.getStakes('0xabcd...');
|
|
94
|
+
### Error Codes
|
|
129
95
|
|
|
130
|
-
|
|
131
|
-
const rewards = await sdk.delegators.getRewards('0xabcd...', 50, 0);
|
|
96
|
+
The SDK recognizes these error codes from the API:
|
|
132
97
|
|
|
133
|
-
|
|
134
|
-
|
|
98
|
+
- **Validator**: `VALIDATOR_NOT_FOUND`, `VALIDATOR_INACTIVE`
|
|
99
|
+
- **Delegator**: `DELEGATOR_NOT_FOUND`, `NOT_WHITELISTED`
|
|
100
|
+
- **Referral**: `REFERRAL_KEY_INVALID`, `REFERRAL_KEY_EXPIRED`, `REFERRAL_KEY_USED`
|
|
101
|
+
- **Auth**: `INVALID_SIGNATURE`, `NONCE_EXPIRED`, `UNAUTHORIZED`
|
|
102
|
+
- **Service**: `RPC_UNAVAILABLE`, `CACHE_UNAVAILABLE`, `DATABASE_UNAVAILABLE`
|
|
103
|
+
- **General**: `BAD_REQUEST`, `INTERNAL_ERROR`, `RATE_LIMITED`
|
|
135
104
|
|
|
136
|
-
|
|
137
|
-
const unbonding = await sdk.delegators.getUnbonding('0xabcd...');
|
|
105
|
+
## Architecture
|
|
138
106
|
|
|
139
|
-
|
|
140
|
-
const validators = await sdk.delegators.getValidators('0xabcd...');
|
|
141
|
-
```
|
|
142
|
-
|
|
143
|
-
### Referrals
|
|
107
|
+
### Caching
|
|
144
108
|
|
|
145
|
-
|
|
146
|
-
// Validate a referral code
|
|
147
|
-
const validation = await sdk.referrals.validate('REF123');
|
|
148
|
-
|
|
149
|
-
// Create a new referral code (requires authentication)
|
|
150
|
-
const referralCode = await sdk.referrals.create({
|
|
151
|
-
validator_address: '0x1234...',
|
|
152
|
-
max_quota: 100,
|
|
153
|
-
expires_in_days: 30,
|
|
154
|
-
});
|
|
109
|
+
The Resonance API implements **server-side Redis caching** with graceful degradation. The SDK does not implement client-side caching as all caching is handled by the API layer. This ensures:
|
|
155
110
|
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
});
|
|
111
|
+
- Consistent data across all API consumers
|
|
112
|
+
- Reduced load on blockchain RPC nodes
|
|
113
|
+
- Automatic cache invalidation on chain state changes
|
|
114
|
+
- Cache TTLs optimized per endpoint (10s to 5min)
|
|
161
115
|
|
|
162
|
-
|
|
163
|
-
await sdk.referrals.delete('REF123');
|
|
116
|
+
### Authentication
|
|
164
117
|
|
|
165
|
-
|
|
166
|
-
await sdk.referrals.unlink('0xabcd...');
|
|
118
|
+
The SDK uses a standard Web3 authentication flow:
|
|
167
119
|
|
|
168
|
-
|
|
169
|
-
|
|
120
|
+
1. Request a nonce from the API (`getNonce`)
|
|
121
|
+
2. Sign the message with your wallet (using viem, wagmi, etc.)
|
|
122
|
+
3. Submit signature for verification (`verify`)
|
|
123
|
+
4. Receive JWT token for authenticated requests
|
|
170
124
|
|
|
171
|
-
|
|
172
|
-
const validatorRef = await sdk.referrals.getValidatorReferral('0x1234...');
|
|
173
|
-
```
|
|
125
|
+
The token is automatically included in all subsequent requests and managed by the client.
|
|
174
126
|
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
```typescript
|
|
178
|
-
// Get all slashing events
|
|
179
|
-
const allEvents = await sdk.slashing.getEvents();
|
|
180
|
-
|
|
181
|
-
// Get slashing events for a specific validator
|
|
182
|
-
const validatorEvents = await sdk.slashing.getEvents('0x1234...', 50, 0);
|
|
183
|
-
```
|
|
127
|
+
## API Reference
|
|
184
128
|
|
|
185
|
-
###
|
|
129
|
+
### Auth
|
|
186
130
|
|
|
187
|
-
|
|
131
|
+
- `getNonce(address)` - Get authentication nonce
|
|
132
|
+
- `verify(address, signature)` - Verify signature and get JWT
|
|
188
133
|
|
|
189
|
-
|
|
190
|
-
// Get protocol-level statistics
|
|
191
|
-
const protocolStats = await sdk.analytics.getProtocolStats();
|
|
192
|
-
console.log('Total Staking:', protocolStats.TotalStaking);
|
|
193
|
-
console.log('Active Validators:', protocolStats.ActiveValidators);
|
|
194
|
-
|
|
195
|
-
// Check sync status of analytics workers
|
|
196
|
-
const syncStatus = await sdk.analytics.getSyncStatus();
|
|
197
|
-
console.log('Protocol Sync Status:', syncStatus.protocol_sync.status);
|
|
198
|
-
console.log('Last Synced Block:', syncStatus.protocol_sync.last_block);
|
|
199
|
-
|
|
200
|
-
// Get all validators with analytics data (paginated)
|
|
201
|
-
const validators = await sdk.analytics.getAllValidators({
|
|
202
|
-
limit: 20,
|
|
203
|
-
offset: 0,
|
|
204
|
-
status: 'active',
|
|
205
|
-
});
|
|
206
|
-
|
|
207
|
-
// Get top validators by uptime
|
|
208
|
-
const topValidators = await sdk.analytics.getTopValidators(10);
|
|
209
|
-
topValidators.data.forEach((v, i) => {
|
|
210
|
-
console.log(`#${i + 1}: ${v.moniker} - ${v.uptime}% uptime`);
|
|
211
|
-
});
|
|
134
|
+
### Validators
|
|
212
135
|
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
136
|
+
- `getValidators()` - Get all validators
|
|
137
|
+
- `getActiveValidators()` - Get active validators
|
|
138
|
+
- `getCandidates()` - Get validator candidates
|
|
139
|
+
- `getValidator(address)` - Get validator details
|
|
140
|
+
- `getValidatorDelegators(address)` - Get validator's delegators
|
|
218
141
|
|
|
219
|
-
|
|
220
|
-
const rewardsPage1 = await sdk.analytics.getValidatorRewards('0x1234...', {
|
|
221
|
-
limit: 50,
|
|
222
|
-
offset: 0,
|
|
223
|
-
});
|
|
142
|
+
### Delegators
|
|
224
143
|
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
144
|
+
- `getDelegator(address)` - Get delegator info
|
|
145
|
+
- `getDelegatorStakes(address)` - Get delegator stakes
|
|
146
|
+
- `getDelegatorRewards(address)` - Get delegator rewards
|
|
228
147
|
|
|
229
|
-
|
|
230
|
-
if (rewardsPage1.metadata.has_more) {
|
|
231
|
-
const rewardsPage2 = await sdk.analytics.getValidatorRewards('0x1234...', {
|
|
232
|
-
limit: 50,
|
|
233
|
-
offset: 50,
|
|
234
|
-
});
|
|
235
|
-
}
|
|
148
|
+
### Referral
|
|
236
149
|
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
maxPages: 10, // Safety limit
|
|
241
|
-
});
|
|
150
|
+
- `getReferralKey(key)` - Get referral key info
|
|
151
|
+
- `getValidatorKeys(address)` - Get validator's referral keys
|
|
152
|
+
- `checkWhitelist(data)` - Check if whitelisted (requires auth)
|
|
242
153
|
|
|
243
|
-
|
|
244
|
-
```
|
|
154
|
+
### Geo
|
|
245
155
|
|
|
246
|
-
|
|
247
|
-
-
|
|
248
|
-
-
|
|
249
|
-
-
|
|
250
|
-
- Use `getSyncStatus()` to verify data freshness before making critical decisions
|
|
156
|
+
- `getGeoNodes()` - Get all geo nodes
|
|
157
|
+
- `getGeoValidators()` - Get validator locations
|
|
158
|
+
- `getGeoStats()` - Get geo statistics
|
|
159
|
+
- `updateGeoLocation(data)` - Update geo location (requires auth)
|
|
251
160
|
|
|
252
|
-
|
|
161
|
+
### Stats
|
|
253
162
|
|
|
254
|
-
|
|
163
|
+
- `getNetworkStats()` - Get network statistics
|
|
164
|
+
- `getCurrentEpoch()` - Get current epoch info
|
|
255
165
|
|
|
256
|
-
|
|
257
|
-
const sdk = new ResonanceSDK({
|
|
258
|
-
apiUrl: 'https://api.fene.network',
|
|
259
|
-
headers: {
|
|
260
|
-
'X-Custom-Header': 'value',
|
|
261
|
-
},
|
|
262
|
-
});
|
|
166
|
+
### APR
|
|
263
167
|
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
```
|
|
168
|
+
- `getNetworkAPR()` - Get network-wide APR
|
|
169
|
+
- `getValidatorAPR(address)` - Get validator APR breakdown
|
|
267
170
|
|
|
268
|
-
###
|
|
171
|
+
### Storage
|
|
269
172
|
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
const validator = await sdk.validators.get('0x1234...');
|
|
273
|
-
} catch (error) {
|
|
274
|
-
if (error instanceof Error) {
|
|
275
|
-
console.error('API Error:', error.message);
|
|
276
|
-
}
|
|
277
|
-
}
|
|
278
|
-
```
|
|
173
|
+
- `uploadAvatar(file)` - Upload avatar (requires auth)
|
|
174
|
+
- `getAvatar(address)` - Get avatar URL
|
|
279
175
|
|
|
280
|
-
###
|
|
176
|
+
### Analytics
|
|
281
177
|
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
apiUrl: 'https://api.fene.network',
|
|
285
|
-
timeout: 60000, // 60 seconds
|
|
286
|
-
});
|
|
287
|
-
```
|
|
178
|
+
- `getDailyBlockStats(days?)` - Get daily block stats
|
|
179
|
+
- `getValidatorRewardHistory(address, limit?)` - Get reward history
|
|
288
180
|
|
|
289
|
-
##
|
|
181
|
+
## Types
|
|
290
182
|
|
|
291
|
-
|
|
183
|
+
All types are exported for TypeScript users:
|
|
292
184
|
|
|
293
185
|
```typescript
|
|
294
186
|
import type {
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
});
|
|
315
|
-
|
|
316
|
-
function ValidatorList() {
|
|
317
|
-
const [validators, setValidators] = useState([]);
|
|
318
|
-
const [loading, setLoading] = useState(true);
|
|
319
|
-
|
|
320
|
-
useEffect(() => {
|
|
321
|
-
const fetchValidators = async () => {
|
|
322
|
-
try {
|
|
323
|
-
const data = await sdk.validators.getAll();
|
|
324
|
-
setValidators(data);
|
|
325
|
-
} catch (error) {
|
|
326
|
-
console.error('Failed to fetch validators:', error);
|
|
327
|
-
} finally {
|
|
328
|
-
setLoading(false);
|
|
329
|
-
}
|
|
330
|
-
};
|
|
331
|
-
|
|
332
|
-
fetchValidators();
|
|
333
|
-
}, []);
|
|
334
|
-
|
|
335
|
-
if (loading) return <div>Loading...</div>;
|
|
336
|
-
|
|
337
|
-
return (
|
|
338
|
-
<div>
|
|
339
|
-
{validators.map((validator) => (
|
|
340
|
-
<div key={validator.address}>{validator.address}</div>
|
|
341
|
-
))}
|
|
342
|
-
</div>
|
|
343
|
-
);
|
|
344
|
-
}
|
|
345
|
-
```
|
|
346
|
-
|
|
347
|
-
## Next.js Example
|
|
348
|
-
|
|
349
|
-
```typescript
|
|
350
|
-
// app/page.tsx
|
|
351
|
-
import { ResonanceSDK } from '@fenelabs/fene-sdk';
|
|
352
|
-
|
|
353
|
-
const sdk = new ResonanceSDK({
|
|
354
|
-
apiUrl: process.env.NEXT_PUBLIC_API_URL || 'https://api.fene.network',
|
|
355
|
-
});
|
|
356
|
-
|
|
357
|
-
export default async function HomePage() {
|
|
358
|
-
const stats = await sdk.global.getStats();
|
|
359
|
-
|
|
360
|
-
return (
|
|
361
|
-
<div>
|
|
362
|
-
<h1>Network Stats</h1>
|
|
363
|
-
<p>Total Validators: {stats.total_validators}</p>
|
|
364
|
-
<p>Total Delegators: {stats.total_delegators}</p>
|
|
365
|
-
<p>Total Stake: {stats.total_network_stake}</p>
|
|
366
|
-
</div>
|
|
367
|
-
);
|
|
368
|
-
}
|
|
187
|
+
Validator,
|
|
188
|
+
Delegator,
|
|
189
|
+
NetworkStats,
|
|
190
|
+
ValidatorAPR,
|
|
191
|
+
// Error types
|
|
192
|
+
ErrorCodeType,
|
|
193
|
+
APIErrorResponse,
|
|
194
|
+
} from "@resonance/sdk";
|
|
195
|
+
|
|
196
|
+
// Error handling utilities
|
|
197
|
+
import {
|
|
198
|
+
ResonanceError,
|
|
199
|
+
ErrorCode,
|
|
200
|
+
isResonanceError,
|
|
201
|
+
hasErrorCode,
|
|
202
|
+
isAuthError,
|
|
203
|
+
isNetworkError,
|
|
204
|
+
isNotFoundError,
|
|
205
|
+
} from "@resonance/sdk";
|
|
369
206
|
```
|
|
370
207
|
|
|
371
|
-
##
|
|
372
|
-
|
|
373
|
-
```typescript
|
|
374
|
-
import { ResonanceSDK } from '@fenelabs/fene-sdk';
|
|
208
|
+
## Development
|
|
375
209
|
|
|
376
|
-
|
|
377
|
-
apiUrl: 'https://api.fene.network',
|
|
378
|
-
});
|
|
210
|
+
### Running Tests
|
|
379
211
|
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
console.log('Network Stats:', stats);
|
|
212
|
+
```bash
|
|
213
|
+
# Run all tests
|
|
214
|
+
pnpm test
|
|
384
215
|
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
console.log('Top 10 Validators:', leaderboard);
|
|
388
|
-
}
|
|
216
|
+
# Run tests in watch mode
|
|
217
|
+
pnpm test -- --watch
|
|
389
218
|
|
|
390
|
-
|
|
219
|
+
# Run tests with coverage
|
|
220
|
+
pnpm test -- --coverage
|
|
391
221
|
```
|
|
392
222
|
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
All API endpoints are available under the `/eth/v1` prefix. The SDK handles this automatically.
|
|
396
|
-
|
|
397
|
-
| Module | Endpoint Pattern | Description |
|
|
398
|
-
|--------|-----------------|-------------|
|
|
399
|
-
| Global | `/eth/v1/global` | Network statistics and leaderboards |
|
|
400
|
-
| Validators | `/eth/v1/validators/:address` | Validator information and history |
|
|
401
|
-
| Delegators | `/eth/v1/delegators/:address` | Delegator information and history |
|
|
402
|
-
| Referrals | `/eth/v1/referrals` | Referral code management |
|
|
403
|
-
| Slashing | `/eth/v1/slashing/events` | Slashing events |
|
|
404
|
-
|
|
405
|
-
## Development
|
|
223
|
+
### Building
|
|
406
224
|
|
|
407
225
|
```bash
|
|
408
|
-
# Install dependencies
|
|
409
|
-
pnpm install
|
|
410
|
-
|
|
411
226
|
# Build the SDK
|
|
412
|
-
pnpm build
|
|
227
|
+
pnpm run build
|
|
413
228
|
|
|
414
|
-
#
|
|
415
|
-
pnpm
|
|
229
|
+
# Watch mode for development
|
|
230
|
+
pnpm run dev
|
|
416
231
|
|
|
417
|
-
#
|
|
418
|
-
pnpm
|
|
232
|
+
# Type checking
|
|
233
|
+
pnpm run lint
|
|
419
234
|
```
|
|
420
235
|
|
|
421
236
|
## License
|
|
422
237
|
|
|
423
238
|
MIT
|
|
424
|
-
|
|
425
|
-
## Support
|
|
426
|
-
|
|
427
|
-
For issues and questions, please visit:
|
|
428
|
-
- GitHub Issues: https://github.com/fenelabs/fene-sdk/issues
|
|
429
|
-
- Documentation: https://docs.fene.network
|