@relaycore/sdk 1.0.0

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/hooks.ts ADDED
@@ -0,0 +1,250 @@
1
+ import { useState, useCallback, useMemo } from 'react';
2
+ import { useAccount, useWalletClient } from 'wagmi';
3
+ import { BrowserProvider } from 'ethers';
4
+ import {
5
+ createConsumerSDK,
6
+ type ServiceQuery,
7
+ type DiscoveredService,
8
+ type ServiceCallResult,
9
+ } from './consumer-sdk';
10
+ import {
11
+ createProviderSDK,
12
+ type ServiceRegistration,
13
+ type RegisteredService,
14
+ type ProviderReputation,
15
+ } from './provider-sdk';
16
+
17
+ /**
18
+ * React hook for Service Consumer SDK
19
+ *
20
+ * Provides easy access to service discovery and calling functionality
21
+ * with automatic wallet integration via wagmi.
22
+ */
23
+ export function useConsumerSDK(config?: { apiUrl?: string }) {
24
+ const { address } = useAccount();
25
+ const { data: walletClient } = useWalletClient();
26
+
27
+ const sdk = useMemo(() => {
28
+ const instance = createConsumerSDK({
29
+ apiUrl: config?.apiUrl,
30
+ network: 'mainnet',
31
+ });
32
+ return instance;
33
+ }, [config?.apiUrl]);
34
+
35
+ // Connect signer when wallet is available
36
+ const connectSigner = useCallback(async () => {
37
+ if (walletClient) {
38
+ const provider = new BrowserProvider(walletClient.transport);
39
+ const signer = await provider.getSigner();
40
+ sdk.connectSigner(signer);
41
+ return true;
42
+ }
43
+ return false;
44
+ }, [walletClient, sdk]);
45
+
46
+ const [loading, setLoading] = useState(false);
47
+ const [error, setError] = useState<string | null>(null);
48
+
49
+ /**
50
+ * Discover services matching criteria
51
+ */
52
+ const discoverServices = useCallback(async (
53
+ query: ServiceQuery
54
+ ): Promise<DiscoveredService[]> => {
55
+ setLoading(true);
56
+ setError(null);
57
+ try {
58
+ return await sdk.discoverServices(query);
59
+ } catch (err) {
60
+ setError((err as Error).message);
61
+ return [];
62
+ } finally {
63
+ setLoading(false);
64
+ }
65
+ }, [sdk]);
66
+
67
+ /**
68
+ * Get a single service
69
+ */
70
+ const getService = useCallback(async (
71
+ serviceId: string
72
+ ): Promise<DiscoveredService | null> => {
73
+ setLoading(true);
74
+ setError(null);
75
+ try {
76
+ return await sdk.getService(serviceId);
77
+ } catch (err) {
78
+ setError((err as Error).message);
79
+ return null;
80
+ } finally {
81
+ setLoading(false);
82
+ }
83
+ }, [sdk]);
84
+
85
+ /**
86
+ * Call a service with automatic payment
87
+ */
88
+ const callService = useCallback(async <T = unknown>(params: {
89
+ serviceId: string;
90
+ endpoint?: string;
91
+ method?: 'GET' | 'POST';
92
+ body?: unknown;
93
+ }): Promise<ServiceCallResult<T>> => {
94
+ setLoading(true);
95
+ setError(null);
96
+ try {
97
+ await connectSigner();
98
+ return await sdk.callService<T>(params);
99
+ } catch (err) {
100
+ setError((err as Error).message);
101
+ return {
102
+ success: false,
103
+ error: (err as Error).message,
104
+ latencyMs: 0,
105
+ };
106
+ } finally {
107
+ setLoading(false);
108
+ }
109
+ }, [sdk, connectSigner]);
110
+
111
+ /**
112
+ * Find compatible services by type
113
+ */
114
+ const findCompatible = useCallback(async (params: {
115
+ inputType?: string;
116
+ outputType?: string;
117
+ tags?: string[];
118
+ }): Promise<DiscoveredService[]> => {
119
+ setLoading(true);
120
+ setError(null);
121
+ try {
122
+ return await sdk.findCompatibleServices(params);
123
+ } catch (err) {
124
+ setError((err as Error).message);
125
+ return [];
126
+ } finally {
127
+ setLoading(false);
128
+ }
129
+ }, [sdk]);
130
+
131
+ return {
132
+ sdk,
133
+ address,
134
+ loading,
135
+ error,
136
+ discoverServices,
137
+ getService,
138
+ callService,
139
+ findCompatible,
140
+ connectSigner,
141
+ };
142
+ }
143
+
144
+ /**
145
+ * React hook for Service Provider SDK
146
+ *
147
+ * Provides easy access to service registration and management
148
+ * with automatic wallet integration via wagmi.
149
+ */
150
+ export function useProviderSDK(config?: { apiUrl?: string }) {
151
+ const { address } = useAccount();
152
+ const { data: walletClient } = useWalletClient();
153
+
154
+ const sdk = useMemo(() => {
155
+ if (!address) return null;
156
+ return createProviderSDK(address, {
157
+ apiUrl: config?.apiUrl,
158
+ });
159
+ }, [address, config?.apiUrl]);
160
+
161
+ // Connect signer when wallet is available
162
+ const connectSigner = useCallback(async () => {
163
+ if (walletClient && sdk) {
164
+ const provider = new BrowserProvider(walletClient.transport);
165
+ const signer = await provider.getSigner();
166
+ sdk.connectSigner(signer);
167
+ return true;
168
+ }
169
+ return false;
170
+ }, [walletClient, sdk]);
171
+
172
+ const [loading, setLoading] = useState(false);
173
+ const [error, setError] = useState<string | null>(null);
174
+
175
+ /**
176
+ * Register a new service
177
+ */
178
+ const registerService = useCallback(async (
179
+ service: ServiceRegistration
180
+ ): Promise<RegisteredService | null> => {
181
+ if (!sdk) {
182
+ setError('Wallet not connected');
183
+ return null;
184
+ }
185
+
186
+ setLoading(true);
187
+ setError(null);
188
+ try {
189
+ return await sdk.registerService(service);
190
+ } catch (err) {
191
+ setError((err as Error).message);
192
+ return null;
193
+ } finally {
194
+ setLoading(false);
195
+ }
196
+ }, [sdk]);
197
+
198
+ /**
199
+ * Get provider reputation
200
+ */
201
+ const getReputation = useCallback(async (): Promise<ProviderReputation | null> => {
202
+ if (!sdk) {
203
+ setError('Wallet not connected');
204
+ return null;
205
+ }
206
+
207
+ setLoading(true);
208
+ setError(null);
209
+ try {
210
+ return await sdk.getReputation();
211
+ } catch (err) {
212
+ setError((err as Error).message);
213
+ return null;
214
+ } finally {
215
+ setLoading(false);
216
+ }
217
+ }, [sdk]);
218
+
219
+ /**
220
+ * Get all services for this provider
221
+ */
222
+ const getMyServices = useCallback(async (): Promise<RegisteredService[]> => {
223
+ if (!sdk) {
224
+ setError('Wallet not connected');
225
+ return [];
226
+ }
227
+
228
+ setLoading(true);
229
+ setError(null);
230
+ try {
231
+ return await sdk.getMyServices();
232
+ } catch (err) {
233
+ setError((err as Error).message);
234
+ return [];
235
+ } finally {
236
+ setLoading(false);
237
+ }
238
+ }, [sdk]);
239
+
240
+ return {
241
+ sdk,
242
+ address,
243
+ loading,
244
+ error,
245
+ registerService,
246
+ getReputation,
247
+ getMyServices,
248
+ connectSigner,
249
+ };
250
+ }
package/index.ts ADDED
@@ -0,0 +1,153 @@
1
+ /**
2
+ * Relay Core SDK
3
+ *
4
+ * Complete SDK for interacting with the Relay Core platform.
5
+ *
6
+ * NEW (Recommended):
7
+ * - RelayAgent - For AI agents to discover, decide, and execute
8
+ * - RelayService - For service providers to expose, deliver, and earn
9
+ *
10
+ * LEGACY (Still supported):
11
+ * - ServiceProviderSDK
12
+ * - ServiceConsumerSDK
13
+ * - AgentSDK
14
+ */
15
+
16
+ // =============================================================================
17
+ // NEW IMPROVED SDKs (Recommended)
18
+ // =============================================================================
19
+
20
+ // RelayAgent - For AI agents
21
+ export {
22
+ RelayAgent,
23
+ createAgent,
24
+ type AgentConfig,
25
+ type TrustPolicy,
26
+ type ServiceCriteria,
27
+ type SelectedService,
28
+ type ExecutionResult,
29
+ type ExecutionError,
30
+ type ErrorCode,
31
+ type WorkflowStep as AgentWorkflowStep,
32
+ type WorkflowResult,
33
+ type OutcomeRecord as AgentOutcome,
34
+ type AgentMemory,
35
+ type AgentCard,
36
+ type AgentCardResource,
37
+ type TaskArtifact,
38
+ type TaskState,
39
+ type TaskStats,
40
+ } from './relay-agent';
41
+
42
+ // RelayService - For service providers
43
+ export {
44
+ RelayService,
45
+ createService,
46
+ defineService,
47
+ hashProof,
48
+ createPaymentMiddleware,
49
+ type ServiceConfig,
50
+ type ServiceDefinition,
51
+ type RegisteredService as ServiceRegistered,
52
+ type PaymentContext,
53
+ type DeliveryProof,
54
+ type PaymentStatus,
55
+ type PaymentEvent,
56
+ type OutcomeType,
57
+ type OutcomeRecord as ServiceOutcome,
58
+ type ServiceMetrics as ServiceMetricsData,
59
+ type ProviderReputation as ServiceReputation,
60
+ type PaymentRequirements as ServicePaymentRequirements,
61
+ type ServiceLogger,
62
+ type JsonSchema,
63
+ } from './relay-service';
64
+
65
+ // =============================================================================
66
+ // LEGACY SDKs (Backwards compatible)
67
+ // =============================================================================
68
+
69
+ // Provider SDK - For registering and managing services
70
+ export {
71
+ ServiceProviderSDK,
72
+ createProviderSDK,
73
+ type ProviderSDKConfig,
74
+ type ServiceRegistration,
75
+ type RegisteredService,
76
+ type ProviderReputation,
77
+ type PaymentReceived,
78
+ type ServiceMetrics,
79
+ } from './provider-sdk';
80
+
81
+ // Consumer SDK - For discovering and calling services
82
+ export {
83
+ ServiceConsumerSDK,
84
+ createConsumerSDK,
85
+ type ConsumerSDKConfig,
86
+ type ServiceQuery,
87
+ type DiscoveredService,
88
+ type PaymentResult,
89
+ type ServiceCallResult,
90
+ type WorkflowStep,
91
+ } from './consumer-sdk';
92
+
93
+ // Legacy Agent SDK (for backwards compatibility)
94
+ export {
95
+ AgentSDK,
96
+ createAgentSDK,
97
+ type AgentService,
98
+ type AgentProfile,
99
+ } from './agent-sdk';
100
+
101
+ // Re-export types for convenience
102
+ export type { PaymentRequirements } from '@crypto.com/facilitator-client';
103
+
104
+ // =============================================================================
105
+ // X402 PROTOCOL (Cronos Standard)
106
+ // =============================================================================
107
+
108
+ export {
109
+ requireX402,
110
+ handleX402Settlement,
111
+ generatePaymentId,
112
+ isEntitled,
113
+ getEntitlement,
114
+ recordEntitlement,
115
+ createPaymentRequirements,
116
+ } from './lib/x402';
117
+
118
+ export type {
119
+ X402Accepts,
120
+ X402Response,
121
+ X402PaidRecord,
122
+ X402PayResult,
123
+ X402ProtectionOptions,
124
+ X402PayParams,
125
+ } from './types/x402.types';
126
+
127
+ // =============================================================================
128
+ // CHAT TYPES (Control Plane Architecture)
129
+ // =============================================================================
130
+
131
+ export type {
132
+ ChatMode,
133
+ ChatResponseType,
134
+ ChatRequest,
135
+ ChatResponse,
136
+ ChatAction,
137
+ SimulationResult,
138
+ } from './types/chat.types';
139
+
140
+ export { CHAT_CAPABILITIES, PROHIBITED_OPERATIONS } from './types/chat.types';
141
+
142
+ // =============================================================================
143
+ // RWA SDK (State Machine & Asset Management)
144
+ // =============================================================================
145
+
146
+ export {
147
+ RelayRWASDK,
148
+ createRWASDK,
149
+ type RWAConfig,
150
+ type RWAStateMachine,
151
+ type TransitionParams,
152
+ type TransitionResult
153
+ } from './relay-rwa';
package/lib/erc8004.ts ADDED
@@ -0,0 +1,51 @@
1
+ import { ethers } from 'ethers';
2
+
3
+ const IDENTITY_REGISTRY_ABI = [
4
+ 'function registerAgent(string memory agentURI, address walletAddress) external returns (uint256)',
5
+ 'event AgentRegistered(uint256 indexed agentId, address indexed owner, string agentURI, address walletAddress)',
6
+ ];
7
+
8
+ export async function registerAgent(
9
+ agentURI: string,
10
+ walletAddress: string,
11
+ signer: ethers.Signer,
12
+ contractAddress: string
13
+ ): Promise<{ agentId: number; txHash: string }> {
14
+ try {
15
+ if (!contractAddress) {
16
+ throw new Error('Identity Registry address not configured');
17
+ }
18
+
19
+ const identityRegistry = new ethers.Contract(
20
+ contractAddress,
21
+ IDENTITY_REGISTRY_ABI,
22
+ signer
23
+ );
24
+
25
+ const tx = await identityRegistry.registerAgent(agentURI, walletAddress);
26
+ const receipt = await tx.wait();
27
+
28
+ // Extract agentId from event
29
+ const event = receipt.logs.find((log: any) => {
30
+ try {
31
+ const parsed = identityRegistry.interface.parseLog(log);
32
+ return parsed?.name === 'AgentRegistered';
33
+ } catch {
34
+ return false;
35
+ }
36
+ });
37
+
38
+ if (event) {
39
+ const parsed = identityRegistry.interface.parseLog(event);
40
+ return {
41
+ agentId: Number(parsed?.args.agentId),
42
+ txHash: receipt.hash,
43
+ };
44
+ }
45
+
46
+ throw new Error('AgentRegistered event not found');
47
+ } catch (error: any) {
48
+ console.error('Failed to register agent:', error);
49
+ throw new Error(`Agent registration failed: ${error.message}`);
50
+ }
51
+ }
@@ -0,0 +1,65 @@
1
+ import { Facilitator, type PaymentRequirements, CronosNetwork } from '@crypto.com/facilitator-client';
2
+
3
+ export class FacilitatorClient {
4
+ private facilitator: Facilitator;
5
+
6
+ constructor(network: CronosNetwork = 'cronos-testnet', privateKey?: string) {
7
+ // If privateKey is provided, set it in process.env for the Facilitator SDK to pick up
8
+ // Note: The Facilitator SDK currently relies on process.env.WALLET_PRIVATE_KEY
9
+ if (privateKey) {
10
+ process.env.WALLET_PRIVATE_KEY = privateKey;
11
+ }
12
+
13
+ this.facilitator = new Facilitator({ network });
14
+ }
15
+
16
+ async settlePayment(params: {
17
+ paymentHeader: string;
18
+ paymentRequirements: PaymentRequirements;
19
+ }) {
20
+ try {
21
+ // Build the verify request
22
+ const verifyRequest = this.facilitator.buildVerifyRequest(
23
+ params.paymentHeader,
24
+ params.paymentRequirements
25
+ );
26
+
27
+ // Step 1: Verify the EIP-3009 authorization
28
+ const verifyResult = await this.facilitator.verifyPayment(verifyRequest);
29
+
30
+ if (!verifyResult.isValid) {
31
+ throw new Error('Payment verification failed: Invalid signature or parameters');
32
+ }
33
+
34
+ // Step 2: Settle the payment on-chain
35
+ const settleResult = await this.facilitator.settlePayment(verifyRequest);
36
+
37
+ return {
38
+ success: true,
39
+ txHash: settleResult.txHash,
40
+ timestamp: Date.now(),
41
+ };
42
+ } catch (error) {
43
+ console.error('Payment settlement error', error);
44
+ throw error;
45
+ }
46
+ }
47
+
48
+ generatePaymentRequirements(params: {
49
+ merchantAddress: string;
50
+ amount: string;
51
+ resourceUrl: string;
52
+ description?: string;
53
+ }): PaymentRequirements {
54
+ return this.facilitator.generatePaymentRequirements({
55
+ payTo: params.merchantAddress,
56
+ maxAmountRequired: params.amount,
57
+ resource: params.resourceUrl,
58
+ description: params.description || 'Protected resource access',
59
+ });
60
+ }
61
+
62
+ getFacilitator(): Facilitator {
63
+ return this.facilitator;
64
+ }
65
+ }
package/lib/ipfs.ts ADDED
@@ -0,0 +1,71 @@
1
+ /**
2
+ * IPFS Metadata Service (SDK Version)
3
+ */
4
+
5
+ export interface AgentMetadata {
6
+ name: string;
7
+ description: string;
8
+ image?: string;
9
+ external_url?: string;
10
+ attributes: {
11
+ trait_type: string;
12
+ value: string | number;
13
+ }[];
14
+ service_type: string;
15
+ endpoint: string;
16
+ price_per_request: string;
17
+ version: string;
18
+ created_at: string;
19
+ }
20
+
21
+ export async function uploadAgentMetadataToIPFS(
22
+ metadata: AgentMetadata,
23
+ apiBaseUrl: string
24
+ ): Promise<string> {
25
+ try {
26
+ const response = await fetch(`${apiBaseUrl}/api/ipfs/upload-metadata`, {
27
+ method: 'POST',
28
+ headers: {
29
+ 'Content-Type': 'application/json',
30
+ },
31
+ body: JSON.stringify(metadata),
32
+ });
33
+
34
+ if (!response.ok) {
35
+ const error = await response.json();
36
+ throw new Error(error.error || 'IPFS upload failed');
37
+ }
38
+
39
+ const result = await response.json();
40
+ return result.ipfsUri;
41
+ } catch (error: unknown) {
42
+ const message = error instanceof Error ? error.message : 'Unknown error';
43
+ throw new Error(`Failed to upload to IPFS: ${message}`);
44
+ }
45
+ }
46
+
47
+ export function buildAgentMetadata(params: {
48
+ name: string;
49
+ description: string;
50
+ serviceType: string;
51
+ endpoint: string;
52
+ pricePerRequest: string;
53
+ imageUri?: string;
54
+ }): AgentMetadata {
55
+ return {
56
+ name: params.name,
57
+ description: params.description,
58
+ image: params.imageUri,
59
+ external_url: 'https://relaycore.xyz',
60
+ attributes: [
61
+ { trait_type: 'Service Type', value: params.serviceType },
62
+ { trait_type: 'Network', value: 'Cronos Testnet' },
63
+ { trait_type: 'Protocol', value: 'x402' },
64
+ ],
65
+ service_type: params.serviceType,
66
+ endpoint: params.endpoint,
67
+ price_per_request: params.pricePerRequest,
68
+ version: '1.0.0',
69
+ created_at: new Date().toISOString(),
70
+ };
71
+ }
@@ -0,0 +1,5 @@
1
+ import { createClient, SupabaseClient } from '@supabase/supabase-js';
2
+
3
+ export function createSupabaseClient(url: string, key: string): SupabaseClient {
4
+ return createClient(url, key);
5
+ }