@highway1/core 0.1.47 → 0.1.51
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/dist/index.d.ts +496 -46
- package/dist/index.js +1034 -626
- package/dist/index.js.map +1 -1
- package/package.json +11 -23
- package/src/discovery/relay-index.ts +98 -0
- package/src/index.ts +9 -3
- package/src/messaging/defense.ts +236 -0
- package/src/messaging/index.ts +5 -0
- package/src/messaging/queue.ts +181 -0
- package/src/messaging/rate-limiter.ts +85 -0
- package/src/messaging/router.ts +121 -327
- package/src/messaging/storage.ts +281 -0
- package/src/messaging/types.ts +149 -0
- package/src/transport/node.ts +3 -1
- package/src/transport/relay-client.ts +390 -0
- package/src/transport/relay-types.ts +195 -0
- package/LICENSE +0 -21
package/dist/index.d.ts
CHANGED
|
@@ -1,5 +1,3 @@
|
|
|
1
|
-
import { Libp2p } from 'libp2p';
|
|
2
|
-
import { PrivateKey } from '@libp2p/interface';
|
|
3
1
|
import { Level } from 'level';
|
|
4
2
|
|
|
5
3
|
interface KeyPair {
|
|
@@ -61,32 +59,6 @@ declare function signMessage(payload: Uint8Array, privateKey: Uint8Array, public
|
|
|
61
59
|
*/
|
|
62
60
|
declare function verifyMessage(signedMessage: SignedMessage, expectedPublicKey: Uint8Array): Promise<boolean>;
|
|
63
61
|
|
|
64
|
-
interface TransportConfig {
|
|
65
|
-
keyPair?: KeyPair;
|
|
66
|
-
listenAddresses?: string[];
|
|
67
|
-
bootstrapPeers?: string[];
|
|
68
|
-
enableDHT?: boolean;
|
|
69
|
-
/** Run as a relay server so NAT'd agents can receive messages through this node */
|
|
70
|
-
enableRelay?: boolean;
|
|
71
|
-
/** Reserve a relay slot on bootstrap nodes so others can reach us (only needed for hw1 join) */
|
|
72
|
-
reserveRelaySlot?: boolean;
|
|
73
|
-
/** Enable mDNS local peer discovery (default: false) */
|
|
74
|
-
enableMDNS?: boolean;
|
|
75
|
-
/** libp2p PrivateKey for persistent PeerID (from @libp2p/crypto) */
|
|
76
|
-
privateKey?: PrivateKey;
|
|
77
|
-
}
|
|
78
|
-
interface ClawiverseNode {
|
|
79
|
-
libp2p: Libp2p;
|
|
80
|
-
start: () => Promise<void>;
|
|
81
|
-
stop: () => Promise<void>;
|
|
82
|
-
getMultiaddrs: () => string[];
|
|
83
|
-
getPeerId: () => string;
|
|
84
|
-
}
|
|
85
|
-
/**
|
|
86
|
-
* Create a Clawiverse transport node with libp2p
|
|
87
|
-
*/
|
|
88
|
-
declare function createNode(config: TransportConfig): Promise<ClawiverseNode>;
|
|
89
|
-
|
|
90
62
|
/**
|
|
91
63
|
* Trust Score System
|
|
92
64
|
*
|
|
@@ -224,6 +196,167 @@ declare function upgradeLegacyCard(legacy: LegacyAgentCard): AgentCard;
|
|
|
224
196
|
*/
|
|
225
197
|
declare function downgradeToLegacyCard(card: AgentCard): LegacyAgentCard;
|
|
226
198
|
|
|
199
|
+
/**
|
|
200
|
+
* CVP-0011: Relay wire protocol types (shared between relay server and relay client)
|
|
201
|
+
*/
|
|
202
|
+
|
|
203
|
+
declare const RELAY_PROTOCOL_VERSION = 1;
|
|
204
|
+
type RelayMessageType = 'HELLO' | 'WELCOME' | 'SEND' | 'DELIVER' | 'DISCOVER' | 'DISCOVERED' | 'PING' | 'PONG' | 'ACK' | 'DELIVERY_REPORT' | 'FETCH_CARD' | 'CARD' | 'GOODBYE' | 'INDEX_SYNC' | 'ROUTE' | 'SYNC_HELLO' | 'SYNC_REQUEST' | 'SYNC_RESPONSE' | 'SYNC_PUSH' | 'SYNC_RECONCILE';
|
|
205
|
+
interface HelloMessage {
|
|
206
|
+
type: 'HELLO';
|
|
207
|
+
protocolVersion: number;
|
|
208
|
+
did: string;
|
|
209
|
+
card: AgentCard;
|
|
210
|
+
timestamp: number;
|
|
211
|
+
signature: Uint8Array;
|
|
212
|
+
extensions?: string[];
|
|
213
|
+
}
|
|
214
|
+
interface WelcomeMessage {
|
|
215
|
+
type: 'WELCOME';
|
|
216
|
+
protocolVersion: number;
|
|
217
|
+
relayId: string;
|
|
218
|
+
peers: number;
|
|
219
|
+
federatedRelays: string[];
|
|
220
|
+
yourAddr: string;
|
|
221
|
+
}
|
|
222
|
+
interface SendMessage {
|
|
223
|
+
type: 'SEND';
|
|
224
|
+
to: string;
|
|
225
|
+
envelope: Uint8Array;
|
|
226
|
+
}
|
|
227
|
+
interface DeliverMessage {
|
|
228
|
+
type: 'DELIVER';
|
|
229
|
+
messageId: string;
|
|
230
|
+
from: string;
|
|
231
|
+
envelope: Uint8Array;
|
|
232
|
+
}
|
|
233
|
+
interface DiscoverMessage {
|
|
234
|
+
type: 'DISCOVER';
|
|
235
|
+
query: string;
|
|
236
|
+
minTrust?: number;
|
|
237
|
+
limit?: number;
|
|
238
|
+
}
|
|
239
|
+
interface DiscoveredAgent {
|
|
240
|
+
did: string;
|
|
241
|
+
card: AgentCard;
|
|
242
|
+
online: boolean;
|
|
243
|
+
homeRelay?: string;
|
|
244
|
+
}
|
|
245
|
+
interface DiscoveredMessage {
|
|
246
|
+
type: 'DISCOVERED';
|
|
247
|
+
agents: DiscoveredAgent[];
|
|
248
|
+
}
|
|
249
|
+
interface AckMessage {
|
|
250
|
+
type: 'ACK';
|
|
251
|
+
messageId: string;
|
|
252
|
+
}
|
|
253
|
+
interface DeliveryReportMessage {
|
|
254
|
+
type: 'DELIVERY_REPORT';
|
|
255
|
+
messageId: string;
|
|
256
|
+
status: 'delivered' | 'expired' | 'queue_full' | 'unknown_recipient';
|
|
257
|
+
timestamp: number;
|
|
258
|
+
}
|
|
259
|
+
interface PingMessage {
|
|
260
|
+
type: 'PING';
|
|
261
|
+
}
|
|
262
|
+
interface PongMessage {
|
|
263
|
+
type: 'PONG';
|
|
264
|
+
peers: number;
|
|
265
|
+
}
|
|
266
|
+
interface FetchCardMessage {
|
|
267
|
+
type: 'FETCH_CARD';
|
|
268
|
+
did: string;
|
|
269
|
+
}
|
|
270
|
+
interface CardMessage {
|
|
271
|
+
type: 'CARD';
|
|
272
|
+
did: string;
|
|
273
|
+
card: AgentCard | null;
|
|
274
|
+
}
|
|
275
|
+
interface GoodbyeMessage {
|
|
276
|
+
type: 'GOODBYE';
|
|
277
|
+
}
|
|
278
|
+
interface PresenceProof {
|
|
279
|
+
did: string;
|
|
280
|
+
homeRelay: string;
|
|
281
|
+
expiry: number;
|
|
282
|
+
signature: Uint8Array;
|
|
283
|
+
}
|
|
284
|
+
interface SyncEvent {
|
|
285
|
+
seq: number;
|
|
286
|
+
type: 'JOIN' | 'LEAVE' | 'UPDATE';
|
|
287
|
+
did: string;
|
|
288
|
+
homeRelay: string;
|
|
289
|
+
cardHash?: string;
|
|
290
|
+
capabilityKeys?: string[];
|
|
291
|
+
online: boolean;
|
|
292
|
+
ts: number;
|
|
293
|
+
presenceProof?: PresenceProof;
|
|
294
|
+
}
|
|
295
|
+
interface IndexSyncMessage {
|
|
296
|
+
type: 'INDEX_SYNC';
|
|
297
|
+
events: SyncEvent[];
|
|
298
|
+
}
|
|
299
|
+
interface RouteMessage {
|
|
300
|
+
type: 'ROUTE';
|
|
301
|
+
to: string;
|
|
302
|
+
envelope: Uint8Array;
|
|
303
|
+
ttl: number;
|
|
304
|
+
}
|
|
305
|
+
interface SyncHelloMessage {
|
|
306
|
+
type: 'SYNC_HELLO';
|
|
307
|
+
relayId: string;
|
|
308
|
+
seq: number;
|
|
309
|
+
}
|
|
310
|
+
interface SyncRequestMessage {
|
|
311
|
+
type: 'SYNC_REQUEST';
|
|
312
|
+
fromSeq: number;
|
|
313
|
+
}
|
|
314
|
+
interface SyncResponseMessage {
|
|
315
|
+
type: 'SYNC_RESPONSE';
|
|
316
|
+
events: SyncEvent[];
|
|
317
|
+
}
|
|
318
|
+
interface SyncPushMessage {
|
|
319
|
+
type: 'SYNC_PUSH';
|
|
320
|
+
event: SyncEvent;
|
|
321
|
+
}
|
|
322
|
+
interface SyncReconcileMessage {
|
|
323
|
+
type: 'SYNC_RECONCILE';
|
|
324
|
+
dids: string[];
|
|
325
|
+
}
|
|
326
|
+
type RelayMessage = HelloMessage | WelcomeMessage | SendMessage | DeliverMessage | DiscoverMessage | DiscoveredMessage | AckMessage | DeliveryReportMessage | PingMessage | PongMessage | FetchCardMessage | CardMessage | GoodbyeMessage | IndexSyncMessage | RouteMessage | SyncHelloMessage | SyncRequestMessage | SyncResponseMessage | SyncPushMessage | SyncReconcileMessage;
|
|
327
|
+
|
|
328
|
+
/**
|
|
329
|
+
* CVP-0011: WebSocket relay client with reconnection logic
|
|
330
|
+
*/
|
|
331
|
+
|
|
332
|
+
interface RelayClientConfig {
|
|
333
|
+
relayUrls: string[];
|
|
334
|
+
did: string;
|
|
335
|
+
keyPair: KeyPair;
|
|
336
|
+
card: AgentCard;
|
|
337
|
+
reconnect?: {
|
|
338
|
+
baseMs?: number;
|
|
339
|
+
jitterMs?: number;
|
|
340
|
+
maxDelayMs?: number;
|
|
341
|
+
stableAfterMs?: number;
|
|
342
|
+
};
|
|
343
|
+
}
|
|
344
|
+
type MessageDeliveryHandler = (msg: DeliverMessage) => Promise<void>;
|
|
345
|
+
type DeliveryReportHandler = (msg: DeliveryReportMessage) => void;
|
|
346
|
+
interface RelayClient {
|
|
347
|
+
start(): Promise<void>;
|
|
348
|
+
stop(): Promise<void>;
|
|
349
|
+
sendEnvelope(toDid: string, envelopeBytes: Uint8Array): Promise<void>;
|
|
350
|
+
discover(query: string, minTrust?: number, limit?: number): Promise<DiscoveredAgent[]>;
|
|
351
|
+
fetchCard(did: string): Promise<AgentCard | null>;
|
|
352
|
+
onDeliver(handler: MessageDeliveryHandler): void;
|
|
353
|
+
onDeliveryReport(handler: DeliveryReportHandler): void;
|
|
354
|
+
isConnected(): boolean;
|
|
355
|
+
getConnectedRelays(): string[];
|
|
356
|
+
getPeerCount(): number;
|
|
357
|
+
}
|
|
358
|
+
declare function createRelayClient(config: RelayClientConfig): RelayClient;
|
|
359
|
+
|
|
227
360
|
/**
|
|
228
361
|
* Create a new Agent Card (Phase 2 format with structured capabilities)
|
|
229
362
|
*/
|
|
@@ -441,22 +574,25 @@ declare class SearchIndex {
|
|
|
441
574
|
private applyFilters;
|
|
442
575
|
}
|
|
443
576
|
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
577
|
+
/**
|
|
578
|
+
* CVP-0011: Relay-backed discovery operations
|
|
579
|
+
* Implements the same DHTOperations interface shape but backed by relay queries
|
|
580
|
+
*/
|
|
581
|
+
|
|
582
|
+
interface RelayIndexOperations {
|
|
449
583
|
publishAgentCard: (card: AgentCard) => Promise<void>;
|
|
450
584
|
queryAgentCard: (did: string) => Promise<AgentCard | null>;
|
|
451
585
|
queryByCapability: (capability: string) => Promise<AgentCard[]>;
|
|
452
586
|
searchSemantic: (query: SemanticQuery) => Promise<AgentCard[]>;
|
|
453
|
-
resolveDID: (did: string) => Promise<
|
|
587
|
+
resolveDID: (did: string) => Promise<{
|
|
588
|
+
relayUrl: string;
|
|
589
|
+
} | null>;
|
|
454
590
|
queryRelayPeers: () => Promise<string[]>;
|
|
455
591
|
}
|
|
456
592
|
/**
|
|
457
|
-
* Create
|
|
593
|
+
* Create relay-backed discovery operations
|
|
458
594
|
*/
|
|
459
|
-
declare function
|
|
595
|
+
declare function createRelayIndexOperations(client: RelayClient): RelayIndexOperations;
|
|
460
596
|
|
|
461
597
|
/**
|
|
462
598
|
* Capability Matcher
|
|
@@ -495,6 +631,19 @@ declare class CapabilityMatcher {
|
|
|
495
631
|
private levenshteinDistance;
|
|
496
632
|
}
|
|
497
633
|
|
|
634
|
+
interface ResolvedDID {
|
|
635
|
+
peerId: string;
|
|
636
|
+
multiaddrs: string[];
|
|
637
|
+
}
|
|
638
|
+
interface DHTOperations {
|
|
639
|
+
publishAgentCard: (card: AgentCard) => Promise<void>;
|
|
640
|
+
queryAgentCard: (did: string) => Promise<AgentCard | null>;
|
|
641
|
+
queryByCapability: (capability: string) => Promise<AgentCard[]>;
|
|
642
|
+
searchSemantic: (query: SemanticQuery) => Promise<AgentCard[]>;
|
|
643
|
+
resolveDID: (did: string) => Promise<ResolvedDID | null>;
|
|
644
|
+
queryRelayPeers: () => Promise<string[]>;
|
|
645
|
+
}
|
|
646
|
+
|
|
498
647
|
/**
|
|
499
648
|
* Semantic Search Engine
|
|
500
649
|
*
|
|
@@ -603,24 +752,229 @@ declare function encodeMessageJSON(envelope: MessageEnvelope): string;
|
|
|
603
752
|
declare function decodeMessageJSON(json: string): MessageEnvelope;
|
|
604
753
|
|
|
605
754
|
type MessageHandler = (envelope: MessageEnvelope) => Promise<MessageEnvelope | void>;
|
|
606
|
-
interface PeerHint {
|
|
607
|
-
peerId: string;
|
|
608
|
-
multiaddrs: string[];
|
|
609
|
-
}
|
|
610
755
|
interface MessageRouter {
|
|
611
756
|
registerHandler: (protocol: string, handler: MessageHandler) => void;
|
|
612
757
|
unregisterHandler: (protocol: string) => void;
|
|
613
758
|
registerCatchAllHandler: (handler: MessageHandler) => void;
|
|
614
|
-
sendMessage: (envelope: MessageEnvelope
|
|
759
|
+
sendMessage: (envelope: MessageEnvelope) => Promise<MessageEnvelope | void>;
|
|
615
760
|
start: () => Promise<void>;
|
|
616
761
|
stop: () => Promise<void>;
|
|
617
762
|
}
|
|
618
763
|
/**
|
|
619
|
-
* Create a message router
|
|
620
|
-
* When dht is provided, sendMessage can resolve DIDs to peer addresses via DHT lookup.
|
|
621
|
-
* When relayPeers is provided, sendMessage will attempt relay fallback if direct dial fails.
|
|
764
|
+
* Create a message router using relay client (CVP-0011)
|
|
622
765
|
*/
|
|
623
|
-
declare function createMessageRouter(
|
|
766
|
+
declare function createMessageRouter(relayClient: RelayClient, verifyFn: (signature: Uint8Array, data: Uint8Array) => Promise<boolean>): MessageRouter;
|
|
767
|
+
|
|
768
|
+
/**
|
|
769
|
+
* Message Queue Types
|
|
770
|
+
*
|
|
771
|
+
* Types for message queue, storage, and filtering operations.
|
|
772
|
+
*/
|
|
773
|
+
|
|
774
|
+
/**
|
|
775
|
+
* Message direction
|
|
776
|
+
*/
|
|
777
|
+
type MessageDirection = 'inbound' | 'outbound';
|
|
778
|
+
/**
|
|
779
|
+
* Message status
|
|
780
|
+
*/
|
|
781
|
+
type MessageStatus = 'pending' | 'delivered' | 'failed' | 'archived';
|
|
782
|
+
/**
|
|
783
|
+
* Stored message with metadata
|
|
784
|
+
*/
|
|
785
|
+
interface StoredMessage {
|
|
786
|
+
envelope: MessageEnvelope;
|
|
787
|
+
direction: MessageDirection;
|
|
788
|
+
status: MessageStatus;
|
|
789
|
+
receivedAt?: number;
|
|
790
|
+
sentAt?: number;
|
|
791
|
+
readAt?: number;
|
|
792
|
+
trustScore?: number;
|
|
793
|
+
error?: string;
|
|
794
|
+
}
|
|
795
|
+
/**
|
|
796
|
+
* Message filter for queries
|
|
797
|
+
*/
|
|
798
|
+
interface MessageFilter {
|
|
799
|
+
fromDid?: string | string[];
|
|
800
|
+
toDid?: string | string[];
|
|
801
|
+
protocol?: string | string[];
|
|
802
|
+
minTrustScore?: number;
|
|
803
|
+
maxAge?: number;
|
|
804
|
+
type?: 'request' | 'response' | 'notification';
|
|
805
|
+
unreadOnly?: boolean;
|
|
806
|
+
status?: MessageStatus | MessageStatus[];
|
|
807
|
+
}
|
|
808
|
+
/**
|
|
809
|
+
* Pagination options
|
|
810
|
+
*/
|
|
811
|
+
interface PaginationOptions {
|
|
812
|
+
limit?: number;
|
|
813
|
+
offset?: number;
|
|
814
|
+
startKey?: string;
|
|
815
|
+
}
|
|
816
|
+
/**
|
|
817
|
+
* Paginated message results
|
|
818
|
+
*/
|
|
819
|
+
interface MessagePage {
|
|
820
|
+
messages: StoredMessage[];
|
|
821
|
+
total: number;
|
|
822
|
+
hasMore: boolean;
|
|
823
|
+
nextKey?: string;
|
|
824
|
+
}
|
|
825
|
+
/**
|
|
826
|
+
* Blocklist entry
|
|
827
|
+
*/
|
|
828
|
+
interface BlocklistEntry {
|
|
829
|
+
did: string;
|
|
830
|
+
reason: string;
|
|
831
|
+
blockedAt: number;
|
|
832
|
+
blockedBy: string;
|
|
833
|
+
}
|
|
834
|
+
/**
|
|
835
|
+
* Allowlist entry
|
|
836
|
+
*/
|
|
837
|
+
interface AllowlistEntry {
|
|
838
|
+
did: string;
|
|
839
|
+
addedAt: number;
|
|
840
|
+
note?: string;
|
|
841
|
+
}
|
|
842
|
+
/**
|
|
843
|
+
* Seen cache entry (for deduplication)
|
|
844
|
+
*/
|
|
845
|
+
interface SeenEntry {
|
|
846
|
+
messageId: string;
|
|
847
|
+
seenAt: number;
|
|
848
|
+
fromDid: string;
|
|
849
|
+
}
|
|
850
|
+
/**
|
|
851
|
+
* Rate limit state
|
|
852
|
+
*/
|
|
853
|
+
interface RateLimitState {
|
|
854
|
+
did: string;
|
|
855
|
+
tokens: number;
|
|
856
|
+
lastRefill: number;
|
|
857
|
+
totalRequests: number;
|
|
858
|
+
firstSeen: number;
|
|
859
|
+
}
|
|
860
|
+
/**
|
|
861
|
+
* Defense check result
|
|
862
|
+
*/
|
|
863
|
+
interface DefenseResult {
|
|
864
|
+
allowed: boolean;
|
|
865
|
+
reason?: 'blocked' | 'duplicate' | 'trust_too_low' | 'rate_limited' | 'invalid';
|
|
866
|
+
trustScore?: number;
|
|
867
|
+
remainingTokens?: number;
|
|
868
|
+
resetTime?: number;
|
|
869
|
+
}
|
|
870
|
+
/**
|
|
871
|
+
* Rate limit result
|
|
872
|
+
*/
|
|
873
|
+
interface RateLimitResult {
|
|
874
|
+
allowed: boolean;
|
|
875
|
+
remaining: number;
|
|
876
|
+
resetTime: number;
|
|
877
|
+
limit: number;
|
|
878
|
+
}
|
|
879
|
+
/**
|
|
880
|
+
* Queue statistics
|
|
881
|
+
*/
|
|
882
|
+
interface QueueStats {
|
|
883
|
+
inboxTotal: number;
|
|
884
|
+
inboxUnread: number;
|
|
885
|
+
outboxPending: number;
|
|
886
|
+
outboxFailed: number;
|
|
887
|
+
blockedAgents: number;
|
|
888
|
+
allowedAgents: number;
|
|
889
|
+
rateLimitedAgents: number;
|
|
890
|
+
}
|
|
891
|
+
/**
|
|
892
|
+
* Subscription callback
|
|
893
|
+
*/
|
|
894
|
+
type MessageCallback = (message: StoredMessage) => void | Promise<void>;
|
|
895
|
+
/**
|
|
896
|
+
* Subscription filter
|
|
897
|
+
*/
|
|
898
|
+
interface SubscriptionFilter extends MessageFilter {
|
|
899
|
+
webhookUrl?: string;
|
|
900
|
+
}
|
|
901
|
+
|
|
902
|
+
/**
|
|
903
|
+
* Message Storage - LevelDB operations for message queue
|
|
904
|
+
*
|
|
905
|
+
* Key schema:
|
|
906
|
+
* msg:inbound:{timestamp}:{id} → StoredMessage
|
|
907
|
+
* msg:outbound:{timestamp}:{id} → StoredMessage
|
|
908
|
+
* block:{did} → BlocklistEntry
|
|
909
|
+
* allow:{did} → AllowlistEntry
|
|
910
|
+
* seen:{messageId} → SeenEntry
|
|
911
|
+
* rate:{did} → RateLimitState
|
|
912
|
+
* idx:from:{did}:{timestamp}:{id} → '1'
|
|
913
|
+
*/
|
|
914
|
+
|
|
915
|
+
declare class MessageStorage {
|
|
916
|
+
private db;
|
|
917
|
+
private ready;
|
|
918
|
+
constructor(dbPath: string);
|
|
919
|
+
open(): Promise<void>;
|
|
920
|
+
close(): Promise<void>;
|
|
921
|
+
putMessage(msg: StoredMessage): Promise<void>;
|
|
922
|
+
getMessage(id: string): Promise<StoredMessage | null>;
|
|
923
|
+
updateMessage(id: string, updates: Partial<StoredMessage>): Promise<void>;
|
|
924
|
+
deleteMessage(id: string): Promise<void>;
|
|
925
|
+
queryMessages(direction: 'inbound' | 'outbound', filter?: MessageFilter, pagination?: PaginationOptions): Promise<MessagePage>;
|
|
926
|
+
private matchesFilter;
|
|
927
|
+
countMessages(direction: 'inbound' | 'outbound', filter?: MessageFilter): Promise<number>;
|
|
928
|
+
putBlock(entry: BlocklistEntry): Promise<void>;
|
|
929
|
+
getBlock(did: string): Promise<BlocklistEntry | null>;
|
|
930
|
+
deleteBlock(did: string): Promise<void>;
|
|
931
|
+
listBlocked(): Promise<BlocklistEntry[]>;
|
|
932
|
+
putAllow(entry: AllowlistEntry): Promise<void>;
|
|
933
|
+
getAllow(did: string): Promise<AllowlistEntry | null>;
|
|
934
|
+
deleteAllow(did: string): Promise<void>;
|
|
935
|
+
listAllowed(): Promise<AllowlistEntry[]>;
|
|
936
|
+
putSeen(entry: SeenEntry): Promise<void>;
|
|
937
|
+
getSeen(messageId: string): Promise<SeenEntry | null>;
|
|
938
|
+
cleanupSeen(maxAgeMs: number): Promise<void>;
|
|
939
|
+
putRateLimit(state: RateLimitState): Promise<void>;
|
|
940
|
+
getRateLimit(did: string): Promise<RateLimitState | null>;
|
|
941
|
+
cleanupRateLimits(maxAgeMs: number): Promise<void>;
|
|
942
|
+
}
|
|
943
|
+
|
|
944
|
+
/**
|
|
945
|
+
* Message Queue
|
|
946
|
+
*
|
|
947
|
+
* Persistent inbox/outbox backed by LevelDB.
|
|
948
|
+
* Supports real-time subscriptions and pagination.
|
|
949
|
+
*/
|
|
950
|
+
|
|
951
|
+
interface MessageQueueConfig {
|
|
952
|
+
dbPath: string;
|
|
953
|
+
}
|
|
954
|
+
declare class MessageQueue {
|
|
955
|
+
private storage;
|
|
956
|
+
private subscriptions;
|
|
957
|
+
private subCounter;
|
|
958
|
+
constructor(config: MessageQueueConfig);
|
|
959
|
+
get store(): MessageStorage;
|
|
960
|
+
start(): Promise<void>;
|
|
961
|
+
stop(): Promise<void>;
|
|
962
|
+
getInbox(filter?: MessageFilter, pagination?: PaginationOptions): Promise<MessagePage>;
|
|
963
|
+
getMessage(id: string): Promise<StoredMessage | null>;
|
|
964
|
+
markAsRead(id: string): Promise<void>;
|
|
965
|
+
deleteMessage(id: string): Promise<void>;
|
|
966
|
+
getOutbox(pagination?: PaginationOptions): Promise<MessagePage>;
|
|
967
|
+
retryMessage(id: string): Promise<void>;
|
|
968
|
+
enqueueInbound(envelope: MessageEnvelope, trustScore?: number): Promise<StoredMessage>;
|
|
969
|
+
enqueueOutbound(envelope: MessageEnvelope): Promise<StoredMessage>;
|
|
970
|
+
markOutboundDelivered(id: string): Promise<void>;
|
|
971
|
+
markOutboundFailed(id: string, error: string): Promise<void>;
|
|
972
|
+
subscribe(filter: SubscriptionFilter, callback: MessageCallback): string;
|
|
973
|
+
unsubscribe(subscriptionId: string): void;
|
|
974
|
+
private notifySubscribers;
|
|
975
|
+
private matchesSubscriptionFilter;
|
|
976
|
+
getStats(): Promise<QueueStats>;
|
|
977
|
+
}
|
|
624
978
|
|
|
625
979
|
/**
|
|
626
980
|
* Sybil Defense Mechanisms
|
|
@@ -886,6 +1240,102 @@ declare class TrustSystem {
|
|
|
886
1240
|
*/
|
|
887
1241
|
declare function createTrustSystem(config: TrustSystemConfig): TrustSystem;
|
|
888
1242
|
|
|
1243
|
+
/**
|
|
1244
|
+
* Token Bucket Rate Limiter
|
|
1245
|
+
*
|
|
1246
|
+
* Classic token bucket algorithm for per-sender rate limiting.
|
|
1247
|
+
* Tokens refill at a constant rate up to capacity.
|
|
1248
|
+
*/
|
|
1249
|
+
interface TokenBucketConfig {
|
|
1250
|
+
capacity: number;
|
|
1251
|
+
refillRate: number;
|
|
1252
|
+
}
|
|
1253
|
+
declare class TokenBucket {
|
|
1254
|
+
private tokens;
|
|
1255
|
+
private lastRefill;
|
|
1256
|
+
private readonly capacity;
|
|
1257
|
+
private readonly refillRate;
|
|
1258
|
+
constructor(config: TokenBucketConfig, initialTokens?: number, lastRefill?: number);
|
|
1259
|
+
/** Attempt to consume one token. Returns true if allowed. */
|
|
1260
|
+
consume(): boolean;
|
|
1261
|
+
getRemaining(): number;
|
|
1262
|
+
/** Milliseconds until at least one token is available */
|
|
1263
|
+
getResetTime(): number;
|
|
1264
|
+
/** Serialize state for persistence */
|
|
1265
|
+
toState(): {
|
|
1266
|
+
tokens: number;
|
|
1267
|
+
lastRefill: number;
|
|
1268
|
+
};
|
|
1269
|
+
private refill;
|
|
1270
|
+
}
|
|
1271
|
+
/**
|
|
1272
|
+
* Rate limiter tiers based on trust score
|
|
1273
|
+
*/
|
|
1274
|
+
interface RateLimitTiers {
|
|
1275
|
+
/** Trust < 0.3: new/unknown agents */
|
|
1276
|
+
newAgent: TokenBucketConfig;
|
|
1277
|
+
/** Trust 0.3–0.6: established agents */
|
|
1278
|
+
established: TokenBucketConfig;
|
|
1279
|
+
/** Trust > 0.6: trusted agents */
|
|
1280
|
+
trusted: TokenBucketConfig;
|
|
1281
|
+
}
|
|
1282
|
+
declare const DEFAULT_RATE_LIMIT_TIERS: RateLimitTiers;
|
|
1283
|
+
declare function getTierConfig(trustScore: number, tiers: RateLimitTiers): TokenBucketConfig;
|
|
1284
|
+
|
|
1285
|
+
/**
|
|
1286
|
+
* Defense Middleware
|
|
1287
|
+
*
|
|
1288
|
+
* Checks incoming messages against:
|
|
1289
|
+
* 1. Allowlist bypass
|
|
1290
|
+
* 2. Blocklist rejection
|
|
1291
|
+
* 3. Deduplication (seen cache)
|
|
1292
|
+
* 4. Trust score filtering
|
|
1293
|
+
* 5. Rate limiting (token bucket, tiered by trust)
|
|
1294
|
+
*/
|
|
1295
|
+
|
|
1296
|
+
interface DefenseConfig {
|
|
1297
|
+
trustSystem: TrustSystem;
|
|
1298
|
+
storage: MessageStorage;
|
|
1299
|
+
/** Minimum trust score to accept messages (0 = accept all) */
|
|
1300
|
+
minTrustScore?: number;
|
|
1301
|
+
/** Auto-block agents below this score */
|
|
1302
|
+
autoBlockThreshold?: number;
|
|
1303
|
+
rateLimitTiers?: RateLimitTiers;
|
|
1304
|
+
/** TTL for seen-cache entries in ms (default: 1 hour) */
|
|
1305
|
+
seenTtlMs?: number;
|
|
1306
|
+
}
|
|
1307
|
+
declare class DefenseMiddleware {
|
|
1308
|
+
private readonly trust;
|
|
1309
|
+
private readonly storage;
|
|
1310
|
+
private readonly minTrustScore;
|
|
1311
|
+
private readonly autoBlockThreshold;
|
|
1312
|
+
private readonly tiers;
|
|
1313
|
+
private readonly seenTtlMs;
|
|
1314
|
+
private readonly seenCache;
|
|
1315
|
+
private readonly MAX_SEEN_CACHE;
|
|
1316
|
+
private readonly buckets;
|
|
1317
|
+
constructor(config: DefenseConfig);
|
|
1318
|
+
/**
|
|
1319
|
+
* Run all defense checks on an incoming message.
|
|
1320
|
+
* Returns { allowed: true } if the message should be processed,
|
|
1321
|
+
* or { allowed: false, reason } if it should be dropped.
|
|
1322
|
+
*/
|
|
1323
|
+
checkMessage(envelope: MessageEnvelope): Promise<DefenseResult>;
|
|
1324
|
+
blockAgent(did: string, reason: string, blockedBy?: string): Promise<void>;
|
|
1325
|
+
unblockAgent(did: string): Promise<void>;
|
|
1326
|
+
isBlocked(did: string): Promise<boolean>;
|
|
1327
|
+
allowAgent(did: string, note?: string): Promise<void>;
|
|
1328
|
+
removeFromAllowlist(did: string): Promise<void>;
|
|
1329
|
+
isAllowed(did: string): Promise<boolean>;
|
|
1330
|
+
checkRateLimit(did: string, trustScore: number): Promise<RateLimitResult>;
|
|
1331
|
+
hasSeen(messageId: string): boolean;
|
|
1332
|
+
markAsSeen(messageId: string): void;
|
|
1333
|
+
/** Periodic cleanup of expired seen entries */
|
|
1334
|
+
cleanupSeen(): Promise<void>;
|
|
1335
|
+
/** Periodic cleanup of stale rate limit buckets (24h inactive) */
|
|
1336
|
+
cleanupRateLimits(): Promise<void>;
|
|
1337
|
+
}
|
|
1338
|
+
|
|
889
1339
|
declare enum LogLevel {
|
|
890
1340
|
DEBUG = 0,
|
|
891
1341
|
INFO = 1,
|
|
@@ -922,4 +1372,4 @@ declare class MessagingError extends ClawiverseError {
|
|
|
922
1372
|
constructor(message: string, details?: unknown);
|
|
923
1373
|
}
|
|
924
1374
|
|
|
925
|
-
export { type AgentCard, CLAWIVERSE_CONTEXT, type Capability, CapabilityMatcher, type CapabilityParameter, CapabilityTypes, type Challenge, type ChallengeSolution, ClawiverseError, type
|
|
1375
|
+
export { type AckMessage, type AgentCard, type AllowlistEntry, type BlocklistEntry, CLAWIVERSE_CONTEXT, type Capability, CapabilityMatcher, type CapabilityParameter, CapabilityTypes, type CardMessage, type Challenge, type ChallengeSolution, ClawiverseError, DEFAULT_RATE_LIMIT_TIERS, type DefenseConfig, DefenseMiddleware, type DefenseResult, type DeliverMessage, type DeliveryReportHandler, type DeliveryReportMessage, type DiscoverMessage, type DiscoveredAgent, type DiscoveredMessage, DiscoveryError, type Endorsement, EndorsementManager, type FetchCardMessage, type GoodbyeMessage, type HelloMessage, IdentityError, type IndexSyncMessage, type Interaction, InteractionHistory, type InteractionStats, type KeyPair, type LegacyAgentCard, LogLevel, Logger, type MessageCallback, type MessageDeliveryHandler, type MessageDirection, type MessageEnvelope, type MessageFilter, type MessageHandler, type MessagePage, MessageQueue, type MessageQueueConfig, type MessageRouter, type MessageStatus, MessageStorage, MessagingError, type PaginationOptions, ParameterTypes, type PeerTrustLevel, type PingMessage, type PongMessage, type PresenceProof, type QueueStats, RELAY_PROTOCOL_VERSION, type RateLimitResult, type RateLimitState, type RateLimitTiers, type RelayClient, type RelayClientConfig, type RelayIndexOperations, type RelayMessage, type RelayMessageType, type RouteMessage, SCHEMA_ORG_CONTEXT, SearchIndex, type SearchResult, type SeenEntry, type SemanticQuery, SemanticSearchEngine, type SendMessage, type SignFunction, type SignedMessage, type StoredMessage, type SubscriptionFilter, SybilDefense, type SyncEvent, type SyncHelloMessage, type SyncPushMessage, type SyncReconcileMessage, type SyncRequestMessage, type SyncResponseMessage, TokenBucket, type TokenBucketConfig, TransportError, TrustMetrics, type TrustScore, TrustSystem, type TrustSystemConfig, type VerifyFunction, type WelcomeMessage, clawiverseContext, createAgentCard, createDefaultTrustScore, createEnvelope, createLegacyAgentCard, createLogger, createMessageRouter, createRelayClient, createRelayIndexOperations, createSemanticSearch, createTrustSystem, decodeAgentCard, decodeFromCBOR, decodeFromJSON, decodeMessage, decodeMessageJSON, deriveDID, downgradeToLegacyCard, encodeForDHT, encodeForWeb, encodeMessage, encodeMessageJSON, exportKeyPair, extractPublicKey, generateKeyPair, getAgentCardContext, getEncodedSize, getTierConfig, importKeyPair, isLegacyCard, isValidContext, matchesCapability, sign, signAgentCard, signEnvelope, signMessage, upgradeLegacyCard, validateAgentCard, validateDID, validateEnvelope, verify, verifyAgentCard, verifyEnvelope, verifyMessage };
|